@cortex-js/compute-engine 0.55.0 → 0.55.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (257) hide show
  1. package/dist/compile.esm.js +2498 -2108
  2. package/dist/compile.min.esm.js +48 -48
  3. package/dist/compile.min.umd.cjs +49 -49
  4. package/dist/compile.umd.cjs +2498 -2108
  5. package/dist/compute-engine.esm.js +1219 -719
  6. package/dist/compute-engine.min.esm.js +73 -73
  7. package/dist/compute-engine.min.umd.cjs +73 -73
  8. package/dist/compute-engine.umd.cjs +1219 -719
  9. package/dist/core.esm.js +1223 -715
  10. package/dist/core.min.esm.js +72 -72
  11. package/dist/core.min.umd.cjs +72 -72
  12. package/dist/core.umd.cjs +1223 -715
  13. package/dist/interval.esm.js +1564 -1412
  14. package/dist/interval.min.esm.js +6 -6
  15. package/dist/interval.min.umd.cjs +6 -6
  16. package/dist/interval.umd.cjs +1564 -1412
  17. package/dist/latex-syntax.esm.js +673 -492
  18. package/dist/latex-syntax.min.esm.js +6 -6
  19. package/dist/latex-syntax.min.umd.cjs +6 -6
  20. package/dist/latex-syntax.umd.cjs +673 -492
  21. package/dist/math-json.esm.js +2 -2
  22. package/dist/math-json.min.esm.js +2 -2
  23. package/dist/math-json.min.umd.cjs +2 -2
  24. package/dist/math-json.umd.cjs +2 -2
  25. package/dist/numerics.esm.js +2 -2
  26. package/dist/numerics.min.esm.js +2 -2
  27. package/dist/numerics.min.umd.cjs +2 -2
  28. package/dist/numerics.umd.cjs +2 -2
  29. package/dist/types/big-decimal/big-decimal.d.ts +1 -1
  30. package/dist/types/big-decimal/index.d.ts +1 -1
  31. package/dist/types/big-decimal/transcendentals.d.ts +1 -1
  32. package/dist/types/big-decimal/utils.d.ts +1 -1
  33. package/dist/types/common/ansi-codes.d.ts +1 -1
  34. package/dist/types/common/configuration-change.d.ts +1 -1
  35. package/dist/types/common/fuzzy-string-match.d.ts +1 -1
  36. package/dist/types/common/grapheme-splitter.d.ts +1 -1
  37. package/dist/types/common/interruptible.d.ts +1 -1
  38. package/dist/types/common/one-of.d.ts +1 -1
  39. package/dist/types/common/signals.d.ts +1 -1
  40. package/dist/types/common/type/ast-nodes.d.ts +1 -1
  41. package/dist/types/common/type/boxed-type.d.ts +1 -1
  42. package/dist/types/common/type/lexer.d.ts +1 -1
  43. package/dist/types/common/type/parse.d.ts +1 -1
  44. package/dist/types/common/type/parser.d.ts +1 -1
  45. package/dist/types/common/type/primitive.d.ts +1 -1
  46. package/dist/types/common/type/reduce.d.ts +1 -1
  47. package/dist/types/common/type/serialize.d.ts +1 -1
  48. package/dist/types/common/type/subtype.d.ts +1 -1
  49. package/dist/types/common/type/type-builder.d.ts +1 -1
  50. package/dist/types/common/type/types.d.ts +1 -1
  51. package/dist/types/common/type/utils.d.ts +1 -1
  52. package/dist/types/common/utils.d.ts +1 -1
  53. package/dist/types/compile.d.ts +1 -1
  54. package/dist/types/compute-engine/assume.d.ts +1 -1
  55. package/dist/types/compute-engine/boxed-expression/abstract-boxed-expression.d.ts +1 -1
  56. package/dist/types/compute-engine/boxed-expression/apply.d.ts +1 -1
  57. package/dist/types/compute-engine/boxed-expression/arithmetic-add.d.ts +1 -1
  58. package/dist/types/compute-engine/boxed-expression/arithmetic-mul-div.d.ts +1 -1
  59. package/dist/types/compute-engine/boxed-expression/arithmetic-power.d.ts +1 -1
  60. package/dist/types/compute-engine/boxed-expression/ascii-math.d.ts +1 -1
  61. package/dist/types/compute-engine/boxed-expression/box.d.ts +1 -1
  62. package/dist/types/compute-engine/boxed-expression/boxed-dictionary.d.ts +1 -1
  63. package/dist/types/compute-engine/boxed-expression/boxed-function.d.ts +1 -1
  64. package/dist/types/compute-engine/boxed-expression/boxed-number.d.ts +1 -1
  65. package/dist/types/compute-engine/boxed-expression/boxed-operator-definition.d.ts +1 -1
  66. package/dist/types/compute-engine/boxed-expression/boxed-patterns.d.ts +1 -1
  67. package/dist/types/compute-engine/boxed-expression/boxed-string.d.ts +1 -1
  68. package/dist/types/compute-engine/boxed-expression/boxed-symbol.d.ts +1 -1
  69. package/dist/types/compute-engine/boxed-expression/boxed-tensor.d.ts +1 -1
  70. package/dist/types/compute-engine/boxed-expression/boxed-value-definition.d.ts +1 -1
  71. package/dist/types/compute-engine/boxed-expression/cache.d.ts +1 -1
  72. package/dist/types/compute-engine/boxed-expression/canonical-utils.d.ts +1 -1
  73. package/dist/types/compute-engine/boxed-expression/canonical.d.ts +1 -1
  74. package/dist/types/compute-engine/boxed-expression/compare.d.ts +1 -1
  75. package/dist/types/compute-engine/boxed-expression/constants.d.ts +1 -1
  76. package/dist/types/compute-engine/boxed-expression/expand.d.ts +1 -1
  77. package/dist/types/compute-engine/boxed-expression/expression-map.d.ts +1 -1
  78. package/dist/types/compute-engine/boxed-expression/factor.d.ts +1 -1
  79. package/dist/types/compute-engine/boxed-expression/flatten.d.ts +1 -1
  80. package/dist/types/compute-engine/boxed-expression/hold.d.ts +1 -1
  81. package/dist/types/compute-engine/boxed-expression/inequality-bounds.d.ts +1 -1
  82. package/dist/types/compute-engine/boxed-expression/init-lazy-refs.d.ts +1 -1
  83. package/dist/types/compute-engine/boxed-expression/invisible-operator.d.ts +1 -1
  84. package/dist/types/compute-engine/boxed-expression/match.d.ts +1 -1
  85. package/dist/types/compute-engine/boxed-expression/negate.d.ts +1 -1
  86. package/dist/types/compute-engine/boxed-expression/numerics.d.ts +1 -1
  87. package/dist/types/compute-engine/boxed-expression/order.d.ts +1 -1
  88. package/dist/types/compute-engine/boxed-expression/pattern-utils.d.ts +1 -1
  89. package/dist/types/compute-engine/boxed-expression/polynomial-degree.d.ts +1 -1
  90. package/dist/types/compute-engine/boxed-expression/polynomials.d.ts +1 -1
  91. package/dist/types/compute-engine/boxed-expression/predicates.d.ts +1 -1
  92. package/dist/types/compute-engine/boxed-expression/rules.d.ts +1 -1
  93. package/dist/types/compute-engine/boxed-expression/serialize.d.ts +1 -1
  94. package/dist/types/compute-engine/boxed-expression/sgn.d.ts +1 -1
  95. package/dist/types/compute-engine/boxed-expression/simplify.d.ts +1 -1
  96. package/dist/types/compute-engine/boxed-expression/solve-linear-system.d.ts +1 -1
  97. package/dist/types/compute-engine/boxed-expression/solve.d.ts +1 -1
  98. package/dist/types/compute-engine/boxed-expression/stochastic-equal.d.ts +1 -1
  99. package/dist/types/compute-engine/boxed-expression/trigonometry.d.ts +1 -1
  100. package/dist/types/compute-engine/boxed-expression/type-guards.d.ts +1 -1
  101. package/dist/types/compute-engine/boxed-expression/utils.d.ts +1 -1
  102. package/dist/types/compute-engine/boxed-expression/validate.d.ts +1 -1
  103. package/dist/types/compute-engine/collection-utils.d.ts +1 -1
  104. package/dist/types/compute-engine/compilation/base-compiler.d.ts +8 -7
  105. package/dist/types/compute-engine/compilation/compile-expression.d.ts +1 -1
  106. package/dist/types/compute-engine/compilation/constant-folding.d.ts +50 -0
  107. package/dist/types/compute-engine/compilation/glsl-target.d.ts +1 -1
  108. package/dist/types/compute-engine/compilation/gpu-target.d.ts +1 -1
  109. package/dist/types/compute-engine/compilation/interval-javascript-target.d.ts +1 -1
  110. package/dist/types/compute-engine/compilation/javascript-target.d.ts +23 -1
  111. package/dist/types/compute-engine/compilation/python-target.d.ts +1 -1
  112. package/dist/types/compute-engine/compilation/types.d.ts +1 -1
  113. package/dist/types/compute-engine/compilation/wgsl-target.d.ts +1 -1
  114. package/dist/types/compute-engine/cost-function.d.ts +1 -1
  115. package/dist/types/compute-engine/engine-assumptions.d.ts +1 -1
  116. package/dist/types/compute-engine/engine-cache.d.ts +1 -1
  117. package/dist/types/compute-engine/engine-common-symbols.d.ts +1 -1
  118. package/dist/types/compute-engine/engine-compilation-targets.d.ts +1 -1
  119. package/dist/types/compute-engine/engine-configuration-lifecycle.d.ts +1 -1
  120. package/dist/types/compute-engine/engine-declarations.d.ts +1 -1
  121. package/dist/types/compute-engine/engine-expression-entrypoints.d.ts +1 -1
  122. package/dist/types/compute-engine/engine-extension-contracts.d.ts +1 -1
  123. package/dist/types/compute-engine/engine-library-bootstrap.d.ts +1 -1
  124. package/dist/types/compute-engine/engine-numeric-configuration.d.ts +1 -1
  125. package/dist/types/compute-engine/engine-runtime-state.d.ts +1 -1
  126. package/dist/types/compute-engine/engine-scope.d.ts +1 -1
  127. package/dist/types/compute-engine/engine-sequences.d.ts +1 -1
  128. package/dist/types/compute-engine/engine-simplification-rules.d.ts +1 -1
  129. package/dist/types/compute-engine/engine-startup-coordinator.d.ts +1 -1
  130. package/dist/types/compute-engine/engine-type-resolver.d.ts +1 -1
  131. package/dist/types/compute-engine/engine-validation-entrypoints.d.ts +1 -1
  132. package/dist/types/compute-engine/free-functions.d.ts +1 -1
  133. package/dist/types/compute-engine/function-utils.d.ts +1 -1
  134. package/dist/types/compute-engine/global-types.d.ts +1 -1
  135. package/dist/types/compute-engine/index.d.ts +1 -1
  136. package/dist/types/compute-engine/interval/arithmetic.d.ts +1 -1
  137. package/dist/types/compute-engine/interval/comparison.d.ts +1 -1
  138. package/dist/types/compute-engine/interval/elementary.d.ts +1 -1
  139. package/dist/types/compute-engine/interval/index.d.ts +1 -1
  140. package/dist/types/compute-engine/interval/trigonometric.d.ts +1 -1
  141. package/dist/types/compute-engine/interval/types.d.ts +1 -1
  142. package/dist/types/compute-engine/interval/util.d.ts +1 -1
  143. package/dist/types/compute-engine/latex-syntax/dictionary/default-dictionary.d.ts +1 -1
  144. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-algebra.d.ts +1 -1
  145. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-arithmetic.d.ts +1 -1
  146. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-calculus.d.ts +1 -1
  147. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-complex.d.ts +1 -1
  148. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-core.d.ts +1 -1
  149. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-linear-algebra.d.ts +1 -1
  150. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-logic.d.ts +3 -1
  151. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-other.d.ts +1 -1
  152. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-relational-operators.d.ts +1 -1
  153. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-sets.d.ts +1 -1
  154. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-statistics.d.ts +1 -1
  155. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-symbols.d.ts +1 -1
  156. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-trigonometry.d.ts +1 -1
  157. package/dist/types/compute-engine/latex-syntax/dictionary/definitions-units.d.ts +1 -1
  158. package/dist/types/compute-engine/latex-syntax/dictionary/definitions.d.ts +1 -1
  159. package/dist/types/compute-engine/latex-syntax/dictionary/indexed-types.d.ts +1 -1
  160. package/dist/types/compute-engine/latex-syntax/latex-syntax.d.ts +1 -1
  161. package/dist/types/compute-engine/latex-syntax/parse-number.d.ts +1 -1
  162. package/dist/types/compute-engine/latex-syntax/parse-symbol.d.ts +1 -1
  163. package/dist/types/compute-engine/latex-syntax/parse.d.ts +11 -1
  164. package/dist/types/compute-engine/latex-syntax/serialize-dms.d.ts +1 -1
  165. package/dist/types/compute-engine/latex-syntax/serialize-number.d.ts +1 -1
  166. package/dist/types/compute-engine/latex-syntax/serializer-style.d.ts +1 -1
  167. package/dist/types/compute-engine/latex-syntax/serializer.d.ts +1 -1
  168. package/dist/types/compute-engine/latex-syntax/tokenizer.d.ts +1 -1
  169. package/dist/types/compute-engine/latex-syntax/types.d.ts +1 -1
  170. package/dist/types/compute-engine/latex-syntax/utils.d.ts +1 -1
  171. package/dist/types/compute-engine/library/arithmetic.d.ts +1 -1
  172. package/dist/types/compute-engine/library/calculus.d.ts +1 -1
  173. package/dist/types/compute-engine/library/collections.d.ts +1 -1
  174. package/dist/types/compute-engine/library/colors.d.ts +1 -1
  175. package/dist/types/compute-engine/library/combinatorics.d.ts +1 -1
  176. package/dist/types/compute-engine/library/complex.d.ts +1 -1
  177. package/dist/types/compute-engine/library/control-structures.d.ts +1 -1
  178. package/dist/types/compute-engine/library/core.d.ts +1 -1
  179. package/dist/types/compute-engine/library/fractals.d.ts +1 -1
  180. package/dist/types/compute-engine/library/library.d.ts +1 -1
  181. package/dist/types/compute-engine/library/linear-algebra.d.ts +1 -1
  182. package/dist/types/compute-engine/library/logic-analysis.d.ts +1 -1
  183. package/dist/types/compute-engine/library/logic.d.ts +1 -1
  184. package/dist/types/compute-engine/library/number-theory.d.ts +1 -1
  185. package/dist/types/compute-engine/library/polynomials.d.ts +1 -1
  186. package/dist/types/compute-engine/library/quantity-arithmetic.d.ts +1 -1
  187. package/dist/types/compute-engine/library/random-expression.d.ts +1 -1
  188. package/dist/types/compute-engine/library/relational-operator.d.ts +1 -1
  189. package/dist/types/compute-engine/library/sets.d.ts +1 -1
  190. package/dist/types/compute-engine/library/statistics.d.ts +1 -1
  191. package/dist/types/compute-engine/library/trigonometry.d.ts +1 -1
  192. package/dist/types/compute-engine/library/type-handlers.d.ts +1 -1
  193. package/dist/types/compute-engine/library/unit-data.d.ts +1 -1
  194. package/dist/types/compute-engine/library/units.d.ts +1 -1
  195. package/dist/types/compute-engine/library/utils.d.ts +1 -1
  196. package/dist/types/compute-engine/numeric-value/big-numeric-value.d.ts +1 -1
  197. package/dist/types/compute-engine/numeric-value/exact-numeric-value.d.ts +1 -1
  198. package/dist/types/compute-engine/numeric-value/machine-numeric-value.d.ts +1 -1
  199. package/dist/types/compute-engine/numeric-value/types.d.ts +1 -1
  200. package/dist/types/compute-engine/numerics/bigint.d.ts +1 -1
  201. package/dist/types/compute-engine/numerics/expression.d.ts +1 -1
  202. package/dist/types/compute-engine/numerics/interval.d.ts +1 -1
  203. package/dist/types/compute-engine/numerics/linear-algebra.d.ts +1 -1
  204. package/dist/types/compute-engine/numerics/monte-carlo.d.ts +1 -1
  205. package/dist/types/compute-engine/numerics/numeric-bigint.d.ts +1 -1
  206. package/dist/types/compute-engine/numerics/numeric-bignum.d.ts +1 -1
  207. package/dist/types/compute-engine/numerics/numeric-complex.d.ts +1 -1
  208. package/dist/types/compute-engine/numerics/numeric.d.ts +1 -1
  209. package/dist/types/compute-engine/numerics/primes.d.ts +1 -1
  210. package/dist/types/compute-engine/numerics/rationals.d.ts +1 -1
  211. package/dist/types/compute-engine/numerics/richardson.d.ts +1 -1
  212. package/dist/types/compute-engine/numerics/special-functions.d.ts +1 -1
  213. package/dist/types/compute-engine/numerics/statistics.d.ts +1 -1
  214. package/dist/types/compute-engine/numerics/strings.d.ts +1 -1
  215. package/dist/types/compute-engine/numerics/types.d.ts +1 -1
  216. package/dist/types/compute-engine/numerics/unit-data.d.ts +1 -1
  217. package/dist/types/compute-engine/oeis.d.ts +1 -1
  218. package/dist/types/compute-engine/sequence.d.ts +1 -1
  219. package/dist/types/compute-engine/symbolic/antiderivative.d.ts +1 -1
  220. package/dist/types/compute-engine/symbolic/derivative.d.ts +1 -1
  221. package/dist/types/compute-engine/symbolic/distribute.d.ts +1 -1
  222. package/dist/types/compute-engine/symbolic/fu-cost.d.ts +1 -1
  223. package/dist/types/compute-engine/symbolic/fu-transforms.d.ts +1 -1
  224. package/dist/types/compute-engine/symbolic/fu.d.ts +1 -1
  225. package/dist/types/compute-engine/symbolic/logic-utils.d.ts +1 -1
  226. package/dist/types/compute-engine/symbolic/simplify-abs.d.ts +1 -1
  227. package/dist/types/compute-engine/symbolic/simplify-divide.d.ts +1 -1
  228. package/dist/types/compute-engine/symbolic/simplify-factorial.d.ts +1 -1
  229. package/dist/types/compute-engine/symbolic/simplify-hyperbolic.d.ts +1 -1
  230. package/dist/types/compute-engine/symbolic/simplify-infinity.d.ts +1 -1
  231. package/dist/types/compute-engine/symbolic/simplify-log.d.ts +1 -1
  232. package/dist/types/compute-engine/symbolic/simplify-logic.d.ts +1 -1
  233. package/dist/types/compute-engine/symbolic/simplify-power.d.ts +1 -1
  234. package/dist/types/compute-engine/symbolic/simplify-product.d.ts +1 -1
  235. package/dist/types/compute-engine/symbolic/simplify-rules.d.ts +1 -1
  236. package/dist/types/compute-engine/symbolic/simplify-sum.d.ts +1 -1
  237. package/dist/types/compute-engine/symbolic/simplify-trig.d.ts +1 -1
  238. package/dist/types/compute-engine/tensor/tensor-fields.d.ts +1 -1
  239. package/dist/types/compute-engine/tensor/tensors.d.ts +1 -1
  240. package/dist/types/compute-engine/types-definitions.d.ts +1 -1
  241. package/dist/types/compute-engine/types-engine.d.ts +1 -1
  242. package/dist/types/compute-engine/types-evaluation.d.ts +1 -1
  243. package/dist/types/compute-engine/types-expression.d.ts +1 -1
  244. package/dist/types/compute-engine/types-kernel-evaluation.d.ts +1 -1
  245. package/dist/types/compute-engine/types-kernel-serialization.d.ts +1 -1
  246. package/dist/types/compute-engine/types-serialization.d.ts +1 -1
  247. package/dist/types/compute-engine/types.d.ts +1 -1
  248. package/dist/types/compute-engine.d.ts +1 -1
  249. package/dist/types/core.d.ts +1 -1
  250. package/dist/types/interval.d.ts +1 -1
  251. package/dist/types/latex-syntax.d.ts +2 -2
  252. package/dist/types/math-json/symbols.d.ts +1 -1
  253. package/dist/types/math-json/types.d.ts +1 -1
  254. package/dist/types/math-json/utils.d.ts +1 -1
  255. package/dist/types/math-json.d.ts +2 -2
  256. package/dist/types/numerics.d.ts +1 -1
  257. package/package.json +1 -1
package/dist/core.umd.cjs CHANGED
@@ -1,4 +1,4 @@
1
- /** ComputeEngineCore 0.55.0 */
1
+ /** ComputeEngineCore 0.55.3 */
2
2
  (function(global,factory){typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : typeof define === 'function' && define.amd ? define(['exports'],factory):(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.ComputeEngineCore = {}));})(this, (function (exports) { 'use strict';
3
3
  var ComputeEngineCore = (() => {
4
4
  var __defProp = Object.defineProperty;
@@ -9573,6 +9573,452 @@ var ComputeEngineCore = (() => {
9573
9573
  return expr2;
9574
9574
  }
9575
9575
 
9576
+ // src/compute-engine/latex-syntax/dictionary/definitions-logic.ts
9577
+ var DEFINITIONS_LOGIC = [
9578
+ // Constants
9579
+ {
9580
+ name: "True",
9581
+ kind: "symbol",
9582
+ latexTrigger: ["\\top"]
9583
+ // ⊤ U+22A4
9584
+ },
9585
+ {
9586
+ kind: "symbol",
9587
+ latexTrigger: "\\mathrm{True}",
9588
+ parse: "True"
9589
+ },
9590
+ {
9591
+ kind: "symbol",
9592
+ latexTrigger: "\\operatorname{True}",
9593
+ parse: "True"
9594
+ },
9595
+ {
9596
+ kind: "symbol",
9597
+ latexTrigger: "\\mathsf{T}",
9598
+ parse: "True"
9599
+ },
9600
+ {
9601
+ name: "False",
9602
+ kind: "symbol",
9603
+ latexTrigger: ["\\bot"]
9604
+ // ⊥ U+22A5
9605
+ },
9606
+ {
9607
+ kind: "symbol",
9608
+ latexTrigger: "\\operatorname{False}",
9609
+ parse: "False"
9610
+ },
9611
+ {
9612
+ kind: "symbol",
9613
+ latexTrigger: "\\mathsf{F}",
9614
+ parse: "False"
9615
+ },
9616
+ // Operators
9617
+ // Logic operators have lower precedence than comparisons (245)
9618
+ // so that `x = 1 \lor x = 2` parses as `(x = 1) \lor (x = 2)`
9619
+ // See https://github.com/cortex-js/compute-engine/issues/243
9620
+ {
9621
+ name: "And",
9622
+ kind: "infix",
9623
+ latexTrigger: ["\\land"],
9624
+ precedence: 235
9625
+ // serialize: '\\land',
9626
+ },
9627
+ { kind: "infix", latexTrigger: ["\\wedge"], parse: "And", precedence: 235 },
9628
+ { kind: "infix", latexTrigger: "\\&", parse: "And", precedence: 235 },
9629
+ {
9630
+ kind: "infix",
9631
+ latexTrigger: "\\operatorname{and}",
9632
+ parse: "And",
9633
+ precedence: 235
9634
+ },
9635
+ {
9636
+ name: "Or",
9637
+ kind: "infix",
9638
+ latexTrigger: ["\\lor"],
9639
+ precedence: 230
9640
+ },
9641
+ { kind: "infix", latexTrigger: ["\\vee"], parse: "Or", precedence: 230 },
9642
+ { kind: "infix", latexTrigger: "\\parallel", parse: "Or", precedence: 230 },
9643
+ {
9644
+ kind: "infix",
9645
+ latexTrigger: "\\operatorname{or}",
9646
+ parse: "Or",
9647
+ precedence: 230
9648
+ },
9649
+ {
9650
+ name: "Xor",
9651
+ kind: "infix",
9652
+ latexTrigger: ["\\veebar"],
9653
+ precedence: 232
9654
+ },
9655
+ // Possible alt: \oplus ⊕ U+2295
9656
+ {
9657
+ name: "Not",
9658
+ kind: "prefix",
9659
+ latexTrigger: ["\\lnot"],
9660
+ precedence: 880
9661
+ },
9662
+ {
9663
+ kind: "prefix",
9664
+ latexTrigger: ["\\neg"],
9665
+ parse: "Not",
9666
+ precedence: 880
9667
+ },
9668
+ {
9669
+ name: "Nand",
9670
+ kind: "infix",
9671
+ latexTrigger: ["\\barwedge"],
9672
+ precedence: 232
9673
+ // serialize: '\\mid',
9674
+ },
9675
+ {
9676
+ name: "Nor",
9677
+ kind: "infix",
9678
+ latexTrigger: ["\u22BD"],
9679
+ // bar vee
9680
+ precedence: 232
9681
+ // serialize: '\\downarrow',
9682
+ },
9683
+ // Functions
9684
+ {
9685
+ kind: "function",
9686
+ symbolTrigger: "and",
9687
+ parse: "And"
9688
+ },
9689
+ {
9690
+ kind: "function",
9691
+ symbolTrigger: "or",
9692
+ parse: "Or"
9693
+ },
9694
+ {
9695
+ kind: "function",
9696
+ symbolTrigger: "not",
9697
+ parse: "Not"
9698
+ },
9699
+ // Relations
9700
+ {
9701
+ name: "Implies",
9702
+ kind: "infix",
9703
+ precedence: 220,
9704
+ associativity: "right",
9705
+ latexTrigger: ["\\implies"],
9706
+ serialize: "\\implies"
9707
+ },
9708
+ {
9709
+ latexTrigger: ["\\Rightarrow"],
9710
+ kind: "infix",
9711
+ precedence: 220,
9712
+ associativity: "right",
9713
+ parse: "Implies"
9714
+ },
9715
+ {
9716
+ latexTrigger: ["\\rightarrow"],
9717
+ kind: "infix",
9718
+ precedence: 220,
9719
+ associativity: "right",
9720
+ parse: "Implies"
9721
+ },
9722
+ {
9723
+ latexTrigger: ["\\Longrightarrow"],
9724
+ kind: "infix",
9725
+ precedence: 220,
9726
+ associativity: "right",
9727
+ parse: "Implies"
9728
+ },
9729
+ {
9730
+ latexTrigger: ["\\longrightarrow"],
9731
+ kind: "infix",
9732
+ precedence: 220,
9733
+ associativity: "right",
9734
+ parse: "Implies"
9735
+ },
9736
+ {
9737
+ // Non-strict mode: => for implies
9738
+ latexTrigger: ["=", ">"],
9739
+ kind: "infix",
9740
+ precedence: 220,
9741
+ associativity: "right",
9742
+ parse: (parser, lhs, until) => {
9743
+ if (parser.options.strict !== false) return null;
9744
+ const rhs = parser.parseExpression({ ...until, minPrec: 220 });
9745
+ if (rhs === null) return null;
9746
+ return ["Implies", lhs, rhs];
9747
+ }
9748
+ },
9749
+ {
9750
+ name: "Equivalent",
9751
+ // MathML: identical to, Mathematica: Congruent
9752
+ latexTrigger: ["\\iff"],
9753
+ kind: "infix",
9754
+ associativity: "right",
9755
+ precedence: 219
9756
+ },
9757
+ {
9758
+ latexTrigger: ["\\Leftrightarrow"],
9759
+ kind: "infix",
9760
+ associativity: "right",
9761
+ precedence: 219,
9762
+ parse: "Equivalent"
9763
+ },
9764
+ {
9765
+ latexTrigger: ["\\leftrightarrow"],
9766
+ kind: "infix",
9767
+ associativity: "right",
9768
+ precedence: 219,
9769
+ parse: "Equivalent"
9770
+ },
9771
+ {
9772
+ latexTrigger: ["\\Longleftrightarrow"],
9773
+ kind: "infix",
9774
+ associativity: "right",
9775
+ precedence: 219,
9776
+ parse: "Equivalent"
9777
+ },
9778
+ {
9779
+ latexTrigger: ["\\longleftrightarrow"],
9780
+ kind: "infix",
9781
+ associativity: "right",
9782
+ precedence: 219,
9783
+ parse: "Equivalent"
9784
+ },
9785
+ {
9786
+ // Non-strict mode: <=> for equivalence
9787
+ latexTrigger: ["<", "=", ">"],
9788
+ kind: "infix",
9789
+ precedence: 219,
9790
+ associativity: "right",
9791
+ parse: (parser, lhs, until) => {
9792
+ if (parser.options.strict !== false) return null;
9793
+ const rhs = parser.parseExpression({ ...until, minPrec: 219 });
9794
+ if (rhs === null) return null;
9795
+ return ["Equivalent", lhs, rhs];
9796
+ }
9797
+ },
9798
+ {
9799
+ latexTrigger: ["\\equiv"],
9800
+ kind: "infix",
9801
+ associativity: "right",
9802
+ precedence: 219,
9803
+ parse: (parser, lhs, terminator) => {
9804
+ const rhs = parser.parseExpression({ ...terminator, minPrec: 219 });
9805
+ const index = parser.index;
9806
+ const modulus = parser.parseExpression({ ...terminator, minPrec: 219 });
9807
+ if (modulus !== null && operator(modulus) === "Mod")
9808
+ return ["Congruent", lhs, rhs, missingIfEmpty(operand(modulus, 1))];
9809
+ parser.index = index;
9810
+ return ["Equivalent", lhs, missingIfEmpty(rhs)];
9811
+ }
9812
+ },
9813
+ {
9814
+ name: "Proves",
9815
+ kind: "infix",
9816
+ latexTrigger: ["\\vdash"],
9817
+ precedence: 220,
9818
+ associativity: "right",
9819
+ serialize: "\\vdash"
9820
+ },
9821
+ {
9822
+ name: "Entails",
9823
+ kind: "infix",
9824
+ latexTrigger: ["\\vDash"],
9825
+ precedence: 220,
9826
+ associativity: "right",
9827
+ serialize: "\\vDash"
9828
+ },
9829
+ {
9830
+ name: "Satisfies",
9831
+ kind: "infix",
9832
+ latexTrigger: ["\\models"],
9833
+ precedence: 220,
9834
+ associativity: "right",
9835
+ serialize: "\\models"
9836
+ },
9837
+ // Quantifiers: for all, exists
9838
+ {
9839
+ name: "ForAll",
9840
+ kind: "prefix",
9841
+ latexTrigger: ["\\forall"],
9842
+ precedence: 200,
9843
+ // Has to be lower than COMPARISON_PRECEDENCE
9844
+ serialize: serializeQuantifier("\\forall"),
9845
+ parse: parseQuantifier("ForAll")
9846
+ },
9847
+ {
9848
+ name: "Exists",
9849
+ kind: "prefix",
9850
+ latexTrigger: ["\\exists"],
9851
+ precedence: 200,
9852
+ // Has to be lower than COMPARISON_PRECEDENCE,
9853
+ serialize: serializeQuantifier("\\exists"),
9854
+ parse: parseQuantifier("Exists")
9855
+ },
9856
+ {
9857
+ name: "ExistsUnique",
9858
+ kind: "prefix",
9859
+ latexTrigger: ["\\exists", "!"],
9860
+ precedence: 200,
9861
+ // Has to be lower than COMPARISON_PRECEDENCE,
9862
+ serialize: serializeQuantifier("\\exists!"),
9863
+ parse: parseQuantifier("ExistsUnique")
9864
+ },
9865
+ {
9866
+ name: "NotForAll",
9867
+ kind: "prefix",
9868
+ latexTrigger: ["\\lnot", "\\forall"],
9869
+ precedence: 200,
9870
+ // Has to be lower than COMPARISON_PRECEDENCE
9871
+ serialize: serializeQuantifier("\\lnot\\forall"),
9872
+ parse: parseQuantifier("NotForAll")
9873
+ },
9874
+ {
9875
+ name: "NotExists",
9876
+ kind: "prefix",
9877
+ latexTrigger: ["\\lnot", "\\exists"],
9878
+ precedence: 200,
9879
+ // Has to be lower than COMPARISON_PRECEDENCE,
9880
+ serialize: serializeQuantifier("\\lnot\\exists"),
9881
+ parse: parseQuantifier("NotExists")
9882
+ },
9883
+ {
9884
+ name: "KroneckerDelta",
9885
+ kind: "prefix",
9886
+ latexTrigger: ["\\delta", "_"],
9887
+ precedence: 200,
9888
+ serialize: (serializer, expr2) => {
9889
+ const args = operands(expr2);
9890
+ if (args.length === 0) return "\\delta";
9891
+ if (args.every((x) => symbol(x)))
9892
+ return `\\delta_{${args.map((arg) => serializer.serialize(arg)).join("")}}`;
9893
+ return `\\delta_{${args.map((arg) => serializer.serialize(arg)).join(", ")}}`;
9894
+ },
9895
+ parse: (parser) => {
9896
+ const group = parser.parseGroup();
9897
+ if (group === null) {
9898
+ const token = parser.parseToken();
9899
+ if (!token) return null;
9900
+ return ["KroneckerDelta", token];
9901
+ }
9902
+ const seq = getSequence(group);
9903
+ if (seq && seq.length <= 2) return ["KroneckerDelta", ...seq];
9904
+ if (operator(group) === "InvisibleOperator")
9905
+ return ["KroneckerDelta", ...operands(group)];
9906
+ if (group !== null) return ["KroneckerDelta", group];
9907
+ return null;
9908
+ }
9909
+ },
9910
+ // Iverson brackets. Also called the "indicator function"
9911
+ // Must have a single argument, a relational expression, i.e.
9912
+ // `[ a = b ]` or `[ x \leq 0 ]`
9913
+ // Otherwise, it gets rejected, it could be something else, like a list or
9914
+ // tuple.
9915
+ {
9916
+ name: "Boole",
9917
+ kind: "matchfix",
9918
+ openTrigger: "[",
9919
+ closeTrigger: "]",
9920
+ // serialize: (serializer: Serializer, expr: MathJsonExpression) => {
9921
+ // const args = ops(expr);
9922
+ // return `[${serializer.serialize(arg)}]`;
9923
+ // },
9924
+ parse: (_parser, body) => {
9925
+ const h = operator(body);
9926
+ if (!h) return null;
9927
+ if (!DEFINITIONS_INEQUALITIES.some((x) => x.name === h)) return null;
9928
+ return ["Boole", body];
9929
+ }
9930
+ },
9931
+ {
9932
+ kind: "matchfix",
9933
+ openTrigger: "\\llbracket",
9934
+ closeTrigger: "\\rrbracket",
9935
+ parse: (_parser, body) => {
9936
+ const h = operator(body);
9937
+ if (!h) return null;
9938
+ if (!DEFINITIONS_INEQUALITIES.some((x) => x.name === h)) return null;
9939
+ return ["Boole", body];
9940
+ }
9941
+ },
9942
+ // Predicate application in First-Order Logic.
9943
+ // ["Predicate", "P", "x", "y"] serializes to "P(x, y)"
9944
+ {
9945
+ name: "Predicate",
9946
+ serialize: (serializer, expr2) => {
9947
+ const args = operands(expr2);
9948
+ if (args.length === 0) return "";
9949
+ const pred = args[0];
9950
+ const predStr = typeof pred === "string" ? pred : serializer.serialize(pred);
9951
+ if (args.length === 1) return predStr;
9952
+ const argStrs = args.slice(1).map((arg) => serializer.serialize(arg));
9953
+ return `${predStr}(${argStrs.join(", ")})`;
9954
+ }
9955
+ }
9956
+ ];
9957
+ function serializeQuantifier(quantifierSymbol) {
9958
+ return (serializer, expr2) => {
9959
+ const args = operands(expr2);
9960
+ if (args.length === 0) return quantifierSymbol;
9961
+ if (args.length === 1)
9962
+ return `${quantifierSymbol} ${serializer.serialize(args[0])}`;
9963
+ const boundVar = serializer.serialize(args[0]);
9964
+ const body = serializer.serialize(args[1]);
9965
+ return `${quantifierSymbol} ${boundVar}, ${body}`;
9966
+ };
9967
+ }
9968
+ function tightBindingCondition(p, terminator) {
9969
+ return p.peek === "\\to" || p.peek === "\\rightarrow" || p.peek === "\\implies" || p.peek === "\\Rightarrow" || p.peek === "\\iff" || p.peek === "\\Leftrightarrow" || p.peek === "\\land" || p.peek === "\\wedge" || p.peek === "\\lor" || p.peek === "\\vee" || (terminator.condition?.(p) ?? false);
9970
+ }
9971
+ function parseQuantifier(kind) {
9972
+ return (parser, terminator) => {
9973
+ const index = parser.index;
9974
+ const useTightBinding = parser.options.quantifierScope !== "loose";
9975
+ const symbol2 = parser.parseSymbol(terminator);
9976
+ if (symbol2) {
9977
+ parser.skipSpace();
9978
+ if (parser.match(",") || parser.match("\\mid") || parser.match(".") || parser.match(":") || parser.match("\\colon")) {
9979
+ const bodyTerminator = useTightBinding ? {
9980
+ ...terminator,
9981
+ condition: (p) => tightBindingCondition(p, terminator)
9982
+ } : terminator;
9983
+ parser.enterQuantifierScope();
9984
+ const body2 = parser.parseExpression(bodyTerminator);
9985
+ parser.exitQuantifierScope();
9986
+ return [kind, symbol2, missingIfEmpty(body2)];
9987
+ }
9988
+ parser.enterQuantifierScope();
9989
+ const body = parser.parseEnclosure();
9990
+ parser.exitQuantifierScope();
9991
+ if (body) return [kind, symbol2, missingIfEmpty(body)];
9992
+ }
9993
+ parser.index = index;
9994
+ const condTerminator = {
9995
+ ...terminator,
9996
+ condition: (p) => p.peek === ":" || p.peek === "\\colon" || (terminator.condition?.(p) ?? false)
9997
+ };
9998
+ const condition = parser.parseExpression(condTerminator);
9999
+ if (condition === null) return null;
10000
+ parser.skipSpace();
10001
+ if (parser.matchAny([",", "\\mid", ":", "\\colon"])) {
10002
+ const bodyTerminator = useTightBinding ? {
10003
+ ...terminator,
10004
+ condition: (p) => tightBindingCondition(p, terminator)
10005
+ } : terminator;
10006
+ parser.enterQuantifierScope();
10007
+ const body = parser.parseExpression(bodyTerminator);
10008
+ parser.exitQuantifierScope();
10009
+ return [kind, condition, missingIfEmpty(body)];
10010
+ }
10011
+ if (parser.match("(")) {
10012
+ parser.enterQuantifierScope();
10013
+ const body = parser.parseExpression(terminator);
10014
+ parser.exitQuantifierScope();
10015
+ if (!parser.match(")")) return null;
10016
+ return [kind, condition, missingIfEmpty(body)];
10017
+ }
10018
+ return null;
10019
+ };
10020
+ }
10021
+
9576
10022
  // src/compute-engine/latex-syntax/dictionary/definitions-core.ts
9577
10023
  function parseSequence(parser, terminator, lhs, prec, sep) {
9578
10024
  if (terminator && terminator.minPrec >= prec) return null;
@@ -10183,6 +10629,120 @@ var ComputeEngineCore = (() => {
10183
10629
  precedence: 21,
10184
10630
  parse: (parser, lhs, until) => parseWhereExpression(parser, lhs, until)
10185
10631
  },
10632
+ // \text{and} — logical conjunction infix
10633
+ {
10634
+ latexTrigger: ["\\text"],
10635
+ kind: "infix",
10636
+ associativity: "right",
10637
+ precedence: 235,
10638
+ // Same as \land
10639
+ parse: (parser, lhs, until) => {
10640
+ const start = parser.index;
10641
+ if (!matchTextKeyword(parser, "and")) {
10642
+ parser.index = start;
10643
+ return null;
10644
+ }
10645
+ const rhs = parser.parseExpression({ ...until, minPrec: 235 });
10646
+ return ["And", lhs, rhs ?? "Nothing"];
10647
+ }
10648
+ },
10649
+ // \text{or} — logical disjunction infix
10650
+ {
10651
+ latexTrigger: ["\\text"],
10652
+ kind: "infix",
10653
+ associativity: "right",
10654
+ precedence: 230,
10655
+ // Same as \lor
10656
+ parse: (parser, lhs, until) => {
10657
+ const start = parser.index;
10658
+ if (!matchTextKeyword(parser, "or")) {
10659
+ parser.index = start;
10660
+ return null;
10661
+ }
10662
+ const rhs = parser.parseExpression({ ...until, minPrec: 230 });
10663
+ return ["Or", lhs, rhs ?? "Nothing"];
10664
+ }
10665
+ },
10666
+ // \text{iff} — biconditional (if and only if)
10667
+ {
10668
+ latexTrigger: ["\\text"],
10669
+ kind: "infix",
10670
+ associativity: "right",
10671
+ precedence: 219,
10672
+ // Same as \iff
10673
+ parse: (parser, lhs, until) => {
10674
+ const start = parser.index;
10675
+ if (!matchTextKeyword(parser, "iff")) {
10676
+ parser.index = start;
10677
+ return null;
10678
+ }
10679
+ const rhs = parser.parseExpression({ ...until, minPrec: 219 });
10680
+ return ["Equivalent", lhs, rhs ?? "Nothing"];
10681
+ }
10682
+ },
10683
+ // \text{if and only if} — verbose biconditional
10684
+ {
10685
+ latexTrigger: ["\\text"],
10686
+ kind: "infix",
10687
+ associativity: "right",
10688
+ precedence: 219,
10689
+ parse: (parser, lhs, until) => {
10690
+ const start = parser.index;
10691
+ if (!matchTextKeyword(parser, "if and only if")) {
10692
+ parser.index = start;
10693
+ return null;
10694
+ }
10695
+ const rhs = parser.parseExpression({ ...until, minPrec: 219 });
10696
+ return ["Equivalent", lhs, rhs ?? "Nothing"];
10697
+ }
10698
+ },
10699
+ // \text{such that} — constraint separator (like : in set-builder notation)
10700
+ {
10701
+ latexTrigger: ["\\text"],
10702
+ kind: "infix",
10703
+ associativity: "right",
10704
+ precedence: 21,
10705
+ // Low precedence to capture full condition (same as 'where')
10706
+ parse: (parser, lhs, until) => {
10707
+ const start = parser.index;
10708
+ if (!matchTextKeyword(parser, "such that")) {
10709
+ parser.index = start;
10710
+ return null;
10711
+ }
10712
+ const rhs = parser.parseExpression({ ...until, minPrec: 21 });
10713
+ return ["Colon", lhs, rhs ?? "Nothing"];
10714
+ }
10715
+ },
10716
+ // \text{for all} — universal quantifier
10717
+ {
10718
+ latexTrigger: ["\\text"],
10719
+ kind: "prefix",
10720
+ precedence: 200,
10721
+ // Same as \forall
10722
+ parse: (parser, until) => {
10723
+ const start = parser.index;
10724
+ if (!matchTextKeyword(parser, "for all")) {
10725
+ parser.index = start;
10726
+ return null;
10727
+ }
10728
+ return parseQuantifier("ForAll")(parser, until);
10729
+ }
10730
+ },
10731
+ // \text{there exists} — existential quantifier
10732
+ {
10733
+ latexTrigger: ["\\text"],
10734
+ kind: "prefix",
10735
+ precedence: 200,
10736
+ // Same as \exists
10737
+ parse: (parser, until) => {
10738
+ const start = parser.index;
10739
+ if (!matchTextKeyword(parser, "there exists")) {
10740
+ parser.index = start;
10741
+ return null;
10742
+ }
10743
+ return parseQuantifier("Exists")(parser, until);
10744
+ }
10745
+ },
10186
10746
  // Block serializer — used by both `where` and semicolon blocks
10187
10747
  {
10188
10748
  name: "Block",
@@ -10298,6 +10858,39 @@ var ComputeEngineCore = (() => {
10298
10858
  parser.parseExpression(until) ?? "Nothing"
10299
10859
  ]
10300
10860
  },
10861
+ // Text serializer — reconstructs \text{...} with inline $...$ for math
10862
+ {
10863
+ name: "Text",
10864
+ serialize: (serializer, expr2) => {
10865
+ const args = operands(expr2);
10866
+ if (args.length === 0) return "";
10867
+ let firstStr = -1;
10868
+ let lastStr = -1;
10869
+ for (let i = 0; i < args.length; i++) {
10870
+ if (stringValue(args[i]) !== null) {
10871
+ if (firstStr < 0) firstStr = i;
10872
+ lastStr = i;
10873
+ }
10874
+ }
10875
+ if (firstStr < 0)
10876
+ return joinLatex(args.map((a) => serializer.serialize(a)));
10877
+ const parts = [];
10878
+ for (let i = 0; i < firstStr; i++)
10879
+ parts.push(serializer.serialize(args[i]));
10880
+ let textContent = "";
10881
+ for (let i = firstStr; i <= lastStr; i++) {
10882
+ const s = stringValue(args[i]);
10883
+ if (s !== null) textContent += sanitizeLatex(s);
10884
+ else if (operator(args[i]) === "Annotated" || operator(args[i]) === "Text")
10885
+ textContent += serializer.serialize(args[i]);
10886
+ else textContent += "$" + serializer.serialize(args[i]) + "$";
10887
+ }
10888
+ parts.push("\\text{" + textContent + "}");
10889
+ for (let i = lastStr + 1; i < args.length; i++)
10890
+ parts.push(serializer.serialize(args[i]));
10891
+ return joinLatex(parts);
10892
+ }
10893
+ },
10301
10894
  {
10302
10895
  name: "String",
10303
10896
  latexTrigger: ["\\text"],
@@ -10688,9 +11281,10 @@ var ComputeEngineCore = (() => {
10688
11281
  } else if (parser.match("\\textcolor")) {
10689
11282
  const pos = parser.index;
10690
11283
  const color = parser.parseStringGroup();
10691
- const body2 = parser.parseExpression();
10692
- if (color !== null && body2 !== null) {
10693
- runs.push(["Annotated", body2, { dict: { color } }]);
11284
+ if (color !== null) {
11285
+ flush();
11286
+ const body2 = parseTextRun(parser);
11287
+ runs.push(["Annotated", body2, dictionaryFromEntries({ color })]);
10694
11288
  } else {
10695
11289
  parser.index = pos;
10696
11290
  text += "\\textcolor";
@@ -10708,6 +11302,7 @@ var ComputeEngineCore = (() => {
10708
11302
  const expr2 = parser.parseExpression() ?? "Nothing";
10709
11303
  parser.skipSpace();
10710
11304
  if (parser.match("<$>")) {
11305
+ flush();
10711
11306
  runs.push(expr2);
10712
11307
  } else {
10713
11308
  text += "$";
@@ -10718,6 +11313,7 @@ var ComputeEngineCore = (() => {
10718
11313
  const expr2 = parser.parseExpression() ?? "Nothing";
10719
11314
  parser.skipSpace();
10720
11315
  if (parser.match("<$$>")) {
11316
+ flush();
10721
11317
  runs.push(expr2);
10722
11318
  } else {
10723
11319
  text += "$$";
@@ -11068,14 +11664,20 @@ var ComputeEngineCore = (() => {
11068
11664
  }
11069
11665
  while (parser.match("<space>")) {
11070
11666
  }
11071
- let text = "";
11072
- while (!parser.atEnd && parser.peek !== "<}>" && parser.peek !== "<space>") {
11073
- const tok = parser.peek;
11074
- if (/^[a-zA-Z]$/.test(tok)) {
11075
- text += tok;
11076
- parser.nextToken();
11667
+ for (let i = 0; i < keyword.length; i++) {
11668
+ if (keyword[i] === " ") {
11669
+ if (!parser.match("<space>")) {
11670
+ parser.index = start;
11671
+ return false;
11672
+ }
11673
+ while (parser.match("<space>")) {
11674
+ }
11077
11675
  } else {
11078
- break;
11676
+ if (parser.peek !== keyword[i]) {
11677
+ parser.index = start;
11678
+ return false;
11679
+ }
11680
+ parser.nextToken();
11079
11681
  }
11080
11682
  }
11081
11683
  while (parser.match("<space>")) {
@@ -11084,10 +11686,6 @@ var ComputeEngineCore = (() => {
11084
11686
  parser.index = start;
11085
11687
  return false;
11086
11688
  }
11087
- if (text !== keyword) {
11088
- parser.index = start;
11089
- return false;
11090
- }
11091
11689
  return true;
11092
11690
  }
11093
11691
  function matchKeyword(parser, keyword) {
@@ -11255,561 +11853,115 @@ var ComputeEngineCore = (() => {
11255
11853
  ["piSymbol", "\\varpi", 982],
11256
11854
  // GREEK PI SYMBOL
11257
11855
  ["rho", "\\rho", 961],
11258
- ["rhoSymbol", "\\varrho", 1009],
11259
- // GREEK RHO SYMBOL
11260
- ["sigma", "\\sigma", 963],
11261
- ["finalSigma", "\\varsigma", 962],
11262
- //GREEK SMALL LETTER FINAL SIGMA
11263
- ["tau", "\\tau", 964],
11264
- ["phi", "\\phi", 981],
11265
- // Note GREEK PHI SYMBOL, but common usage in math
11266
- ["phiLetter", "\\varphi", 966],
11267
- ["upsilon", "\\upsilon", 965],
11268
- ["chi", "\\chi", 967],
11269
- ["psi", "\\psi", 968],
11270
- ["omega", "\\omega", 969],
11271
- ["Alpha", "\\Alpha", 913],
11272
- ["Beta", "\\Beta", 914],
11273
- ["Gamma", "\\Gamma", 915],
11274
- ["Delta", "\\Delta", 916],
11275
- ["Epsilon", "\\Epsilon", 917],
11276
- ["Zeta", "\\Zeta", 918],
11277
- ["Eta", "\\Eta", 919],
11278
- ["Theta", "\\Theta", 920],
11279
- ["Iota", "\\Iota", 921],
11280
- ["Kappa", "\\Kappa", 922],
11281
- ["Lambda", "\\Lambda", 923],
11282
- ["Mu", "\\Mu", 924],
11283
- ["Nu", "\\Nu", 925],
11284
- ["Xi", "\\Xi", 926],
11285
- ["Omicron", "\\Omicron", 927],
11286
- // ['Pi', '\\Pi', 0x03a0],
11287
- ["Rho", "\\Rho", 929],
11288
- ["Sigma", "\\Sigma", 931],
11289
- ["Tau", "\\Tau", 932],
11290
- ["Phi", "\\Phi", 934],
11291
- ["Upsilon", "\\Upsilon", 933],
11292
- ["Chi", "\\Chi", 935],
11293
- ["Psi", "\\Psi", 936],
11294
- ["Omega", "\\Omega", 937],
11295
- ["digamma", "\\digamma", 989],
11296
- // Hebrew
11297
- ["aleph", "\\aleph", 8501],
11298
- // Unicode ALEF SYMBOL
11299
- ["bet", "\\beth", 8502],
11300
- ["gimel", "\\gimel", 8503],
11301
- ["dalet", "\\daleth", 8504],
11302
- // Letter-like
11303
- ["ell", "\\ell", 8499],
11304
- // Unicode SCRIPT SMALL L
11305
- ["turnedCapitalF", "\\Finv", 8498],
11306
- // Unicode TURNED CAPITAL F'
11307
- ["turnedCapitalG", "\\Game", 8513],
11308
- // TURNED SANS-SERIF CAPITAL G
11309
- ["weierstrass", "\\wp", 8472],
11310
- // Unicode SCRIPT CAPITAL P
11311
- ["eth", "\\eth", 240],
11312
- ["invertedOhm", "\\mho", 8487],
11313
- // Unicode INVERTED OHM SIGN
11314
- ["hBar", "\\hbar", 295],
11315
- // Unicode LATIN SMALL LETTER H WITH STROKE
11316
- ["hSlash", "\\hslash", 8463],
11317
- // Unicode PLANCK CONSTANT OVER TWO PI
11318
- // Symbols
11319
- ["blackClubSuit", "\\clubsuit", 9827],
11320
- ["whiteHeartSuit", "\\heartsuit", 9825],
11321
- ["blackSpadeSuit", "\\spadesuit", 9824],
11322
- ["whiteDiamondSuit", "\\diamondsuit", 9826],
11323
- ["sharp", "\\sharp", 9839],
11324
- ["flat", "\\flat", 9837],
11325
- ["natural", "\\natural", 9838]
11326
- ];
11327
- var DEFINITIONS_SYMBOLS = [
11328
- ...SYMBOLS2.map(([symbol2, latex, _codepoint]) => {
11329
- return {
11330
- kind: "symbol",
11331
- name: symbol2,
11332
- latexTrigger: [latex],
11333
- parse: symbol2
11334
- };
11335
- }),
11336
- ...SYMBOLS2.map(([symbol2, _latex, codepoint]) => {
11337
- return {
11338
- kind: "symbol",
11339
- latexTrigger: [String.fromCodePoint(codepoint)],
11340
- parse: symbol2
11341
- };
11342
- })
11343
- ];
11344
-
11345
- // src/compute-engine/latex-syntax/dictionary/definitions-algebra.ts
11346
- var DEFINITIONS_ALGEBRA = [
11347
- {
11348
- name: "To",
11349
- latexTrigger: ["\\to"],
11350
- kind: "infix",
11351
- precedence: 270
11352
- // MathML rightwards arrow
11353
- },
11354
- {
11355
- // Non-strict mode: -> for maps-to arrow
11356
- latexTrigger: ["-", ">"],
11357
- kind: "infix",
11358
- precedence: 270,
11359
- parse: (parser, lhs, until) => {
11360
- if (parser.options.strict !== false) return null;
11361
- const rhs = parser.parseExpression({ ...until, minPrec: 270 });
11362
- if (rhs === null) return null;
11363
- return ["To", lhs, rhs];
11364
- }
11365
- }
11366
- ];
11367
-
11368
- // src/compute-engine/latex-syntax/dictionary/definitions-logic.ts
11369
- var DEFINITIONS_LOGIC = [
11370
- // Constants
11371
- {
11372
- name: "True",
11373
- kind: "symbol",
11374
- latexTrigger: ["\\top"]
11375
- // ⊤ U+22A4
11376
- },
11377
- {
11378
- kind: "symbol",
11379
- latexTrigger: "\\mathrm{True}",
11380
- parse: "True"
11381
- },
11382
- {
11383
- kind: "symbol",
11384
- latexTrigger: "\\operatorname{True}",
11385
- parse: "True"
11386
- },
11387
- {
11388
- kind: "symbol",
11389
- latexTrigger: "\\mathsf{T}",
11390
- parse: "True"
11391
- },
11392
- {
11393
- name: "False",
11394
- kind: "symbol",
11395
- latexTrigger: ["\\bot"]
11396
- // ⊥ U+22A5
11397
- },
11398
- {
11399
- kind: "symbol",
11400
- latexTrigger: "\\operatorname{False}",
11401
- parse: "False"
11402
- },
11403
- {
11404
- kind: "symbol",
11405
- latexTrigger: "\\mathsf{F}",
11406
- parse: "False"
11407
- },
11408
- // Operators
11409
- // Logic operators have lower precedence than comparisons (245)
11410
- // so that `x = 1 \lor x = 2` parses as `(x = 1) \lor (x = 2)`
11411
- // See https://github.com/cortex-js/compute-engine/issues/243
11412
- {
11413
- name: "And",
11414
- kind: "infix",
11415
- latexTrigger: ["\\land"],
11416
- precedence: 235
11417
- // serialize: '\\land',
11418
- },
11419
- { kind: "infix", latexTrigger: ["\\wedge"], parse: "And", precedence: 235 },
11420
- { kind: "infix", latexTrigger: "\\&", parse: "And", precedence: 235 },
11421
- {
11422
- kind: "infix",
11423
- latexTrigger: "\\operatorname{and}",
11424
- parse: "And",
11425
- precedence: 235
11426
- },
11427
- {
11428
- name: "Or",
11429
- kind: "infix",
11430
- latexTrigger: ["\\lor"],
11431
- precedence: 230
11432
- },
11433
- { kind: "infix", latexTrigger: ["\\vee"], parse: "Or", precedence: 230 },
11434
- { kind: "infix", latexTrigger: "\\parallel", parse: "Or", precedence: 230 },
11435
- {
11436
- kind: "infix",
11437
- latexTrigger: "\\operatorname{or}",
11438
- parse: "Or",
11439
- precedence: 230
11440
- },
11441
- {
11442
- name: "Xor",
11443
- kind: "infix",
11444
- latexTrigger: ["\\veebar"],
11445
- precedence: 232
11446
- },
11447
- // Possible alt: \oplus ⊕ U+2295
11448
- {
11449
- name: "Not",
11450
- kind: "prefix",
11451
- latexTrigger: ["\\lnot"],
11452
- precedence: 880
11453
- },
11454
- {
11455
- kind: "prefix",
11456
- latexTrigger: ["\\neg"],
11457
- parse: "Not",
11458
- precedence: 880
11459
- },
11460
- {
11461
- name: "Nand",
11462
- kind: "infix",
11463
- latexTrigger: ["\\barwedge"],
11464
- precedence: 232
11465
- // serialize: '\\mid',
11466
- },
11467
- {
11468
- name: "Nor",
11469
- kind: "infix",
11470
- latexTrigger: ["\u22BD"],
11471
- // bar vee
11472
- precedence: 232
11473
- // serialize: '\\downarrow',
11474
- },
11475
- // Functions
11476
- {
11477
- kind: "function",
11478
- symbolTrigger: "and",
11479
- parse: "And"
11480
- },
11481
- {
11482
- kind: "function",
11483
- symbolTrigger: "or",
11484
- parse: "Or"
11485
- },
11486
- {
11487
- kind: "function",
11488
- symbolTrigger: "not",
11489
- parse: "Not"
11490
- },
11491
- // Relations
11492
- {
11493
- name: "Implies",
11494
- kind: "infix",
11495
- precedence: 220,
11496
- associativity: "right",
11497
- latexTrigger: ["\\implies"],
11498
- serialize: "\\implies"
11499
- },
11500
- {
11501
- latexTrigger: ["\\Rightarrow"],
11502
- kind: "infix",
11503
- precedence: 220,
11504
- associativity: "right",
11505
- parse: "Implies"
11506
- },
11507
- {
11508
- latexTrigger: ["\\rightarrow"],
11509
- kind: "infix",
11510
- precedence: 220,
11511
- associativity: "right",
11512
- parse: "Implies"
11513
- },
11514
- {
11515
- latexTrigger: ["\\Longrightarrow"],
11516
- kind: "infix",
11517
- precedence: 220,
11518
- associativity: "right",
11519
- parse: "Implies"
11520
- },
11521
- {
11522
- latexTrigger: ["\\longrightarrow"],
11523
- kind: "infix",
11524
- precedence: 220,
11525
- associativity: "right",
11526
- parse: "Implies"
11527
- },
11528
- {
11529
- // Non-strict mode: => for implies
11530
- latexTrigger: ["=", ">"],
11531
- kind: "infix",
11532
- precedence: 220,
11533
- associativity: "right",
11534
- parse: (parser, lhs, until) => {
11535
- if (parser.options.strict !== false) return null;
11536
- const rhs = parser.parseExpression({ ...until, minPrec: 220 });
11537
- if (rhs === null) return null;
11538
- return ["Implies", lhs, rhs];
11539
- }
11540
- },
11541
- {
11542
- name: "Equivalent",
11543
- // MathML: identical to, Mathematica: Congruent
11544
- latexTrigger: ["\\iff"],
11545
- kind: "infix",
11546
- associativity: "right",
11547
- precedence: 219
11548
- },
11549
- {
11550
- latexTrigger: ["\\Leftrightarrow"],
11551
- kind: "infix",
11552
- associativity: "right",
11553
- precedence: 219,
11554
- parse: "Equivalent"
11555
- },
11556
- {
11557
- latexTrigger: ["\\leftrightarrow"],
11558
- kind: "infix",
11559
- associativity: "right",
11560
- precedence: 219,
11561
- parse: "Equivalent"
11562
- },
11563
- {
11564
- latexTrigger: ["\\Longleftrightarrow"],
11565
- kind: "infix",
11566
- associativity: "right",
11567
- precedence: 219,
11568
- parse: "Equivalent"
11569
- },
11856
+ ["rhoSymbol", "\\varrho", 1009],
11857
+ // GREEK RHO SYMBOL
11858
+ ["sigma", "\\sigma", 963],
11859
+ ["finalSigma", "\\varsigma", 962],
11860
+ //GREEK SMALL LETTER FINAL SIGMA
11861
+ ["tau", "\\tau", 964],
11862
+ ["phi", "\\phi", 981],
11863
+ // Note GREEK PHI SYMBOL, but common usage in math
11864
+ ["phiLetter", "\\varphi", 966],
11865
+ ["upsilon", "\\upsilon", 965],
11866
+ ["chi", "\\chi", 967],
11867
+ ["psi", "\\psi", 968],
11868
+ ["omega", "\\omega", 969],
11869
+ ["Alpha", "\\Alpha", 913],
11870
+ ["Beta", "\\Beta", 914],
11871
+ ["Gamma", "\\Gamma", 915],
11872
+ ["Delta", "\\Delta", 916],
11873
+ ["Epsilon", "\\Epsilon", 917],
11874
+ ["Zeta", "\\Zeta", 918],
11875
+ ["Eta", "\\Eta", 919],
11876
+ ["Theta", "\\Theta", 920],
11877
+ ["Iota", "\\Iota", 921],
11878
+ ["Kappa", "\\Kappa", 922],
11879
+ ["Lambda", "\\Lambda", 923],
11880
+ ["Mu", "\\Mu", 924],
11881
+ ["Nu", "\\Nu", 925],
11882
+ ["Xi", "\\Xi", 926],
11883
+ ["Omicron", "\\Omicron", 927],
11884
+ // ['Pi', '\\Pi', 0x03a0],
11885
+ ["Rho", "\\Rho", 929],
11886
+ ["Sigma", "\\Sigma", 931],
11887
+ ["Tau", "\\Tau", 932],
11888
+ ["Phi", "\\Phi", 934],
11889
+ ["Upsilon", "\\Upsilon", 933],
11890
+ ["Chi", "\\Chi", 935],
11891
+ ["Psi", "\\Psi", 936],
11892
+ ["Omega", "\\Omega", 937],
11893
+ ["digamma", "\\digamma", 989],
11894
+ // Hebrew
11895
+ ["aleph", "\\aleph", 8501],
11896
+ // Unicode ALEF SYMBOL
11897
+ ["bet", "\\beth", 8502],
11898
+ ["gimel", "\\gimel", 8503],
11899
+ ["dalet", "\\daleth", 8504],
11900
+ // Letter-like
11901
+ ["ell", "\\ell", 8499],
11902
+ // Unicode SCRIPT SMALL L
11903
+ ["turnedCapitalF", "\\Finv", 8498],
11904
+ // Unicode TURNED CAPITAL F'
11905
+ ["turnedCapitalG", "\\Game", 8513],
11906
+ // TURNED SANS-SERIF CAPITAL G
11907
+ ["weierstrass", "\\wp", 8472],
11908
+ // Unicode SCRIPT CAPITAL P
11909
+ ["eth", "\\eth", 240],
11910
+ ["invertedOhm", "\\mho", 8487],
11911
+ // Unicode INVERTED OHM SIGN
11912
+ ["hBar", "\\hbar", 295],
11913
+ // Unicode LATIN SMALL LETTER H WITH STROKE
11914
+ ["hSlash", "\\hslash", 8463],
11915
+ // Unicode PLANCK CONSTANT OVER TWO PI
11916
+ // Symbols
11917
+ ["blackClubSuit", "\\clubsuit", 9827],
11918
+ ["whiteHeartSuit", "\\heartsuit", 9825],
11919
+ ["blackSpadeSuit", "\\spadesuit", 9824],
11920
+ ["whiteDiamondSuit", "\\diamondsuit", 9826],
11921
+ ["sharp", "\\sharp", 9839],
11922
+ ["flat", "\\flat", 9837],
11923
+ ["natural", "\\natural", 9838]
11924
+ ];
11925
+ var DEFINITIONS_SYMBOLS = [
11926
+ ...SYMBOLS2.map(([symbol2, latex, _codepoint]) => {
11927
+ return {
11928
+ kind: "symbol",
11929
+ name: symbol2,
11930
+ latexTrigger: [latex],
11931
+ parse: symbol2
11932
+ };
11933
+ }),
11934
+ ...SYMBOLS2.map(([symbol2, _latex, codepoint]) => {
11935
+ return {
11936
+ kind: "symbol",
11937
+ latexTrigger: [String.fromCodePoint(codepoint)],
11938
+ parse: symbol2
11939
+ };
11940
+ })
11941
+ ];
11942
+
11943
+ // src/compute-engine/latex-syntax/dictionary/definitions-algebra.ts
11944
+ var DEFINITIONS_ALGEBRA = [
11570
11945
  {
11571
- latexTrigger: ["\\longleftrightarrow"],
11946
+ name: "To",
11947
+ latexTrigger: ["\\to"],
11572
11948
  kind: "infix",
11573
- associativity: "right",
11574
- precedence: 219,
11575
- parse: "Equivalent"
11949
+ precedence: 270
11950
+ // MathML rightwards arrow
11576
11951
  },
11577
11952
  {
11578
- // Non-strict mode: <=> for equivalence
11579
- latexTrigger: ["<", "=", ">"],
11953
+ // Non-strict mode: -> for maps-to arrow
11954
+ latexTrigger: ["-", ">"],
11580
11955
  kind: "infix",
11581
- precedence: 219,
11582
- associativity: "right",
11956
+ precedence: 270,
11583
11957
  parse: (parser, lhs, until) => {
11584
11958
  if (parser.options.strict !== false) return null;
11585
- const rhs = parser.parseExpression({ ...until, minPrec: 219 });
11959
+ const rhs = parser.parseExpression({ ...until, minPrec: 270 });
11586
11960
  if (rhs === null) return null;
11587
- return ["Equivalent", lhs, rhs];
11588
- }
11589
- },
11590
- {
11591
- latexTrigger: ["\\equiv"],
11592
- kind: "infix",
11593
- associativity: "right",
11594
- precedence: 219,
11595
- parse: (parser, lhs, terminator) => {
11596
- const rhs = parser.parseExpression({ ...terminator, minPrec: 219 });
11597
- const index = parser.index;
11598
- const modulus = parser.parseExpression({ ...terminator, minPrec: 219 });
11599
- if (modulus !== null && operator(modulus) === "Mod")
11600
- return ["Congruent", lhs, rhs, missingIfEmpty(operand(modulus, 1))];
11601
- parser.index = index;
11602
- return ["Equivalent", lhs, missingIfEmpty(rhs)];
11603
- }
11604
- },
11605
- {
11606
- name: "Proves",
11607
- kind: "infix",
11608
- latexTrigger: ["\\vdash"],
11609
- precedence: 220,
11610
- associativity: "right",
11611
- serialize: "\\vdash"
11612
- },
11613
- {
11614
- name: "Entails",
11615
- kind: "infix",
11616
- latexTrigger: ["\\vDash"],
11617
- precedence: 220,
11618
- associativity: "right",
11619
- serialize: "\\vDash"
11620
- },
11621
- {
11622
- name: "Satisfies",
11623
- kind: "infix",
11624
- latexTrigger: ["\\models"],
11625
- precedence: 220,
11626
- associativity: "right",
11627
- serialize: "\\models"
11628
- },
11629
- // Quantifiers: for all, exists
11630
- {
11631
- name: "ForAll",
11632
- kind: "prefix",
11633
- latexTrigger: ["\\forall"],
11634
- precedence: 200,
11635
- // Has to be lower than COMPARISON_PRECEDENCE
11636
- serialize: serializeQuantifier("\\forall"),
11637
- parse: parseQuantifier("ForAll")
11638
- },
11639
- {
11640
- name: "Exists",
11641
- kind: "prefix",
11642
- latexTrigger: ["\\exists"],
11643
- precedence: 200,
11644
- // Has to be lower than COMPARISON_PRECEDENCE,
11645
- serialize: serializeQuantifier("\\exists"),
11646
- parse: parseQuantifier("Exists")
11647
- },
11648
- {
11649
- name: "ExistsUnique",
11650
- kind: "prefix",
11651
- latexTrigger: ["\\exists", "!"],
11652
- precedence: 200,
11653
- // Has to be lower than COMPARISON_PRECEDENCE,
11654
- serialize: serializeQuantifier("\\exists!"),
11655
- parse: parseQuantifier("ExistsUnique")
11656
- },
11657
- {
11658
- name: "NotForAll",
11659
- kind: "prefix",
11660
- latexTrigger: ["\\lnot", "\\forall"],
11661
- precedence: 200,
11662
- // Has to be lower than COMPARISON_PRECEDENCE
11663
- serialize: serializeQuantifier("\\lnot\\forall"),
11664
- parse: parseQuantifier("NotForAll")
11665
- },
11666
- {
11667
- name: "NotExists",
11668
- kind: "prefix",
11669
- latexTrigger: ["\\lnot", "\\exists"],
11670
- precedence: 200,
11671
- // Has to be lower than COMPARISON_PRECEDENCE,
11672
- serialize: serializeQuantifier("\\lnot\\exists"),
11673
- parse: parseQuantifier("NotExists")
11674
- },
11675
- {
11676
- name: "KroneckerDelta",
11677
- kind: "prefix",
11678
- latexTrigger: ["\\delta", "_"],
11679
- precedence: 200,
11680
- serialize: (serializer, expr2) => {
11681
- const args = operands(expr2);
11682
- if (args.length === 0) return "\\delta";
11683
- if (args.every((x) => symbol(x)))
11684
- return `\\delta_{${args.map((arg) => serializer.serialize(arg)).join("")}}`;
11685
- return `\\delta_{${args.map((arg) => serializer.serialize(arg)).join(", ")}}`;
11686
- },
11687
- parse: (parser) => {
11688
- const group = parser.parseGroup();
11689
- if (group === null) {
11690
- const token = parser.parseToken();
11691
- if (!token) return null;
11692
- return ["KroneckerDelta", token];
11693
- }
11694
- const seq = getSequence(group);
11695
- if (seq && seq.length <= 2) return ["KroneckerDelta", ...seq];
11696
- if (operator(group) === "InvisibleOperator")
11697
- return ["KroneckerDelta", ...operands(group)];
11698
- if (group !== null) return ["KroneckerDelta", group];
11699
- return null;
11700
- }
11701
- },
11702
- // Iverson brackets. Also called the "indicator function"
11703
- // Must have a single argument, a relational expression, i.e.
11704
- // `[ a = b ]` or `[ x \leq 0 ]`
11705
- // Otherwise, it gets rejected, it could be something else, like a list or
11706
- // tuple.
11707
- {
11708
- name: "Boole",
11709
- kind: "matchfix",
11710
- openTrigger: "[",
11711
- closeTrigger: "]",
11712
- // serialize: (serializer: Serializer, expr: MathJsonExpression) => {
11713
- // const args = ops(expr);
11714
- // return `[${serializer.serialize(arg)}]`;
11715
- // },
11716
- parse: (_parser, body) => {
11717
- const h = operator(body);
11718
- if (!h) return null;
11719
- if (!DEFINITIONS_INEQUALITIES.some((x) => x.name === h)) return null;
11720
- return ["Boole", body];
11721
- }
11722
- },
11723
- {
11724
- kind: "matchfix",
11725
- openTrigger: "\\llbracket",
11726
- closeTrigger: "\\rrbracket",
11727
- parse: (_parser, body) => {
11728
- const h = operator(body);
11729
- if (!h) return null;
11730
- if (!DEFINITIONS_INEQUALITIES.some((x) => x.name === h)) return null;
11731
- return ["Boole", body];
11732
- }
11733
- },
11734
- // Predicate application in First-Order Logic.
11735
- // ["Predicate", "P", "x", "y"] serializes to "P(x, y)"
11736
- {
11737
- name: "Predicate",
11738
- serialize: (serializer, expr2) => {
11739
- const args = operands(expr2);
11740
- if (args.length === 0) return "";
11741
- const pred = args[0];
11742
- const predStr = typeof pred === "string" ? pred : serializer.serialize(pred);
11743
- if (args.length === 1) return predStr;
11744
- const argStrs = args.slice(1).map((arg) => serializer.serialize(arg));
11745
- return `${predStr}(${argStrs.join(", ")})`;
11961
+ return ["To", lhs, rhs];
11746
11962
  }
11747
11963
  }
11748
11964
  ];
11749
- function serializeQuantifier(quantifierSymbol) {
11750
- return (serializer, expr2) => {
11751
- const args = operands(expr2);
11752
- if (args.length === 0) return quantifierSymbol;
11753
- if (args.length === 1)
11754
- return `${quantifierSymbol} ${serializer.serialize(args[0])}`;
11755
- const boundVar = serializer.serialize(args[0]);
11756
- const body = serializer.serialize(args[1]);
11757
- return `${quantifierSymbol} ${boundVar}, ${body}`;
11758
- };
11759
- }
11760
- function tightBindingCondition(p, terminator) {
11761
- return p.peek === "\\to" || p.peek === "\\rightarrow" || p.peek === "\\implies" || p.peek === "\\Rightarrow" || p.peek === "\\iff" || p.peek === "\\Leftrightarrow" || p.peek === "\\land" || p.peek === "\\wedge" || p.peek === "\\lor" || p.peek === "\\vee" || (terminator.condition?.(p) ?? false);
11762
- }
11763
- function parseQuantifier(kind) {
11764
- return (parser, terminator) => {
11765
- const index = parser.index;
11766
- const useTightBinding = parser.options.quantifierScope !== "loose";
11767
- const symbol2 = parser.parseSymbol(terminator);
11768
- if (symbol2) {
11769
- parser.skipSpace();
11770
- if (parser.match(",") || parser.match("\\mid") || parser.match(".") || parser.match(":") || parser.match("\\colon")) {
11771
- const bodyTerminator = useTightBinding ? {
11772
- ...terminator,
11773
- condition: (p) => tightBindingCondition(p, terminator)
11774
- } : terminator;
11775
- parser.enterQuantifierScope();
11776
- const body2 = parser.parseExpression(bodyTerminator);
11777
- parser.exitQuantifierScope();
11778
- return [kind, symbol2, missingIfEmpty(body2)];
11779
- }
11780
- parser.enterQuantifierScope();
11781
- const body = parser.parseEnclosure();
11782
- parser.exitQuantifierScope();
11783
- if (body) return [kind, symbol2, missingIfEmpty(body)];
11784
- }
11785
- parser.index = index;
11786
- const condTerminator = {
11787
- ...terminator,
11788
- condition: (p) => p.peek === ":" || p.peek === "\\colon" || (terminator.condition?.(p) ?? false)
11789
- };
11790
- const condition = parser.parseExpression(condTerminator);
11791
- if (condition === null) return null;
11792
- parser.skipSpace();
11793
- if (parser.matchAny([",", "\\mid", ":", "\\colon"])) {
11794
- const bodyTerminator = useTightBinding ? {
11795
- ...terminator,
11796
- condition: (p) => tightBindingCondition(p, terminator)
11797
- } : terminator;
11798
- parser.enterQuantifierScope();
11799
- const body = parser.parseExpression(bodyTerminator);
11800
- parser.exitQuantifierScope();
11801
- return [kind, condition, missingIfEmpty(body)];
11802
- }
11803
- if (parser.match("(")) {
11804
- parser.enterQuantifierScope();
11805
- const body = parser.parseExpression(terminator);
11806
- parser.exitQuantifierScope();
11807
- if (!parser.match(")")) return null;
11808
- return [kind, condition, missingIfEmpty(body)];
11809
- }
11810
- return null;
11811
- };
11812
- }
11813
11965
 
11814
11966
  // src/compute-engine/latex-syntax/dictionary/definitions-sets.ts
11815
11967
  function parseIntervalBody(body, openLeft, openRight) {
@@ -16315,7 +16467,7 @@ var ComputeEngineCore = (() => {
16315
16467
  var FLAG_SEQUENCE = "\\p{RI}\\p{RI}";
16316
16468
  var TAG_MOD = `(?:[\\u{E0020}-\\u{E007E}]+\\u{E007F})`;
16317
16469
  var EMOJI_MOD = `(?:\\p{EMod}|${VS16}${KEYCAP}?|${TAG_MOD})`;
16318
- var EMOJI_NOT_SYMBOL = `(?:(?=\\P{XIDC})\\p{Emoji})`;
16470
+ var EMOJI_NOT_SYMBOL = `(?:(?=\\P{XIDC})(?=[^\\x23\\x2a\\x30-\\x39])\\p{Emoji})`;
16319
16471
  var ZWJ_ELEMENT = `(?:${EMOJI_NOT_SYMBOL}${EMOJI_MOD}*|\\p{Emoji}${EMOJI_MOD}+|${FLAG_SEQUENCE})`;
16320
16472
  var POSSIBLE_EMOJI = `(?:${ZWJ_ELEMENT})(${ZWJ2}${ZWJ_ELEMENT})*`;
16321
16473
  var SOME_EMOJI = new RegExp(`(?:${POSSIBLE_EMOJI})+`, "u");
@@ -17024,7 +17176,9 @@ var ComputeEngineCore = (() => {
17024
17176
  }
17025
17177
  return c;
17026
17178
  }
17027
- return parser.nextToken();
17179
+ const raw = parser.peek;
17180
+ if (raw && /^[\p{XIDC}\p{M}]/u.test(raw)) return parser.nextToken();
17181
+ return null;
17028
17182
  }
17029
17183
  function parseSymbolBody(parser) {
17030
17184
  let id = matchPrefixedSymbol(parser);
@@ -18314,6 +18468,29 @@ var ComputeEngineCore = (() => {
18314
18468
  this.index = start;
18315
18469
  return null;
18316
18470
  }
18471
+ /**
18472
+ * Speculatively check if any \text infix entry (e.g. "and", "or", "where")
18473
+ * would match the upcoming tokens. This is used to prevent InvisibleOperator
18474
+ * from consuming \text{keyword} as a text run when the keyword is actually
18475
+ * an infix operator that was skipped due to precedence constraints.
18476
+ *
18477
+ * Returns true if any entry's parse function would succeed (non-null result).
18478
+ * The parser index is always restored to its original position.
18479
+ */
18480
+ wouldMatchTextInfix(opDefs) {
18481
+ const start = this.index;
18482
+ for (const [def, n] of opDefs) {
18483
+ if (def.kind !== "infix") continue;
18484
+ this.index = start + n;
18485
+ const result = def.parse(this, "Nothing", { minPrec: 0 });
18486
+ if (result !== null) {
18487
+ this.index = start;
18488
+ return true;
18489
+ }
18490
+ }
18491
+ this.index = start;
18492
+ return false;
18493
+ }
18317
18494
  /**
18318
18495
  * This returns an array of arguments (as in a function application),
18319
18496
  * or null if there is no match.
@@ -18939,6 +19116,7 @@ var ComputeEngineCore = (() => {
18939
19116
  if (isDelimiterCommand(this))
18940
19117
  return this.error("unexpected-delimiter", start);
18941
19118
  if (command[0] !== "\\") {
19119
+ this.nextToken();
18942
19120
  return this.error(
18943
19121
  ["unexpected-token", { str: tokensToString(command) }],
18944
19122
  start
@@ -19067,25 +19245,28 @@ var ComputeEngineCore = (() => {
19067
19245
  if (result === null && until.minPrec <= INVISIBLE_OP_PRECEDENCE) {
19068
19246
  const opDefs = this.peekDefinitions("operator");
19069
19247
  if (opDefs.length === 0 || opDefs.every(([def]) => def.latexTrigger === "\\text")) {
19070
- const rhs = this.parseExpression({
19071
- ...until,
19072
- minPrec: INVISIBLE_OP_PRECEDENCE + 1
19073
- });
19074
- if (rhs !== null) {
19075
- if (operator(lhs) === "InvisibleOperator") {
19076
- if (operator(rhs) === "InvisibleOperator")
19077
- result = [
19078
- "InvisibleOperator",
19079
- ...operands(lhs),
19080
- ...operands(rhs)
19081
- ];
19082
- else result = ["InvisibleOperator", ...operands(lhs), rhs];
19083
- } else if (operator(rhs) === "InvisibleOperator") {
19084
- result = ["InvisibleOperator", lhs, ...operands(rhs)];
19085
- } else result = ["InvisibleOperator", lhs, rhs];
19248
+ if (opDefs.length > 0 && this.wouldMatchTextInfix(opDefs)) {
19086
19249
  } else {
19087
- if (result === null) {
19088
- result = this.options.parseUnexpectedToken?.(lhs, this) ?? null;
19250
+ const rhs = this.parseExpression({
19251
+ ...until,
19252
+ minPrec: INVISIBLE_OP_PRECEDENCE + 1
19253
+ });
19254
+ if (rhs !== null) {
19255
+ if (operator(lhs) === "InvisibleOperator") {
19256
+ if (operator(rhs) === "InvisibleOperator")
19257
+ result = [
19258
+ "InvisibleOperator",
19259
+ ...operands(lhs),
19260
+ ...operands(rhs)
19261
+ ];
19262
+ else result = ["InvisibleOperator", ...operands(lhs), rhs];
19263
+ } else if (operator(rhs) === "InvisibleOperator") {
19264
+ result = ["InvisibleOperator", lhs, ...operands(rhs)];
19265
+ } else result = ["InvisibleOperator", lhs, rhs];
19266
+ } else {
19267
+ if (result === null) {
19268
+ result = this.options.parseUnexpectedToken?.(lhs, this) ?? null;
19269
+ }
19089
19270
  }
19090
19271
  }
19091
19272
  }
@@ -30550,8 +30731,7 @@ ${lines.join("\n")}`;
30550
30731
  broadcastable: true,
30551
30732
  idempotent: true,
30552
30733
  complexity: 1200,
30553
- signature: "(number) -> number",
30554
- type: ([x]) => x.type,
30734
+ signature: "(number) -> real",
30555
30735
  sgn: ([x]) => {
30556
30736
  if (x.isSame(0)) return "zero";
30557
30737
  if (isNumber(x)) return "positive";
@@ -37910,6 +38090,10 @@ ${e.message}
37910
38090
  scoped: true,
37911
38091
  lazy: true,
37912
38092
  signature: "(expression, variable:symbol, variables:symbol+) -> expression",
38093
+ type: ([body]) => {
38094
+ if (body && body.type.matches("number")) return body.type;
38095
+ return void 0;
38096
+ },
37913
38097
  canonical: (ops, { engine: ce, scope }) => {
37914
38098
  if (isSymbol2(ops[0]) && ops[0].canonical.operatorDefinition) {
37915
38099
  const vars = ops.slice(1);
@@ -42481,6 +42665,18 @@ ${e.message}
42481
42665
  }
42482
42666
  }
42483
42667
  ops = flattenInvisibleOperator(ops);
42668
+ if (ops.some((op) => isFunction2(op, "Text") || isString(op))) {
42669
+ const runs = [];
42670
+ for (const op of ops) {
42671
+ if (isFunction2(op, "Text")) {
42672
+ runs.push(...op.ops);
42673
+ } else if (op.operator !== "HorizontalSpacing") {
42674
+ runs.push(op.canonical);
42675
+ }
42676
+ }
42677
+ return ce._fn("Text", runs);
42678
+ }
42679
+ ops = combineFunctionApplications(ce, ops);
42484
42680
  {
42485
42681
  const significant = ops.filter((x) => x.operator !== "HorizontalSpacing");
42486
42682
  if (significant.length === 2) {
@@ -42495,7 +42691,7 @@ ${e.message}
42495
42691
  }
42496
42692
  ops = flatten(ops);
42497
42693
  if (ops.every(
42498
- (x) => x.isValid && (x.type.isUnknown || x.type.matches("number") || x.isIndexedCollection && !isString(x))
42694
+ (x) => x.isValid && (x.type.isUnknown || x.type.type === "any" || x.type.type === "expression" || x.type.matches("number") || x.isIndexedCollection && !isString(x))
42499
42695
  )) {
42500
42696
  return ce._fn("Multiply", ops);
42501
42697
  }
@@ -42510,6 +42706,40 @@ ${e.message}
42510
42706
  }
42511
42707
  return ys;
42512
42708
  }
42709
+ function combineFunctionApplications(ce, ops) {
42710
+ const result = [];
42711
+ let i = 0;
42712
+ while (i < ops.length) {
42713
+ const op = ops[i];
42714
+ if (i < ops.length - 1 && isSymbol2(op) && isFunction2(ops[i + 1], "Delimiter")) {
42715
+ const symName = op.symbol;
42716
+ const def = ce.lookupDefinition(symName);
42717
+ const delim = ops[i + 1];
42718
+ if (def && (isOperatorDef(def) || def.value?.type?.matches("function"))) {
42719
+ let args = delim.op1 ? isFunction2(delim.op1, "Sequence") ? delim.op1.ops : [delim.op1] : [];
42720
+ args = flatten(args);
42721
+ result.push(ce.function(symName, args));
42722
+ i += 2;
42723
+ continue;
42724
+ }
42725
+ if (delim.op1 && isFunction2(delim.op1, "Sequence")) {
42726
+ let args = delim.op1.ops;
42727
+ args = flatten(args);
42728
+ if (args.length > 1) {
42729
+ if (!def) ce.declare(symName, "function");
42730
+ else if (!isOperatorDef(def) && def.value?.type?.isUnknown)
42731
+ op.canonical.infer("function");
42732
+ result.push(ce.function(symName, args));
42733
+ i += 2;
42734
+ continue;
42735
+ }
42736
+ }
42737
+ }
42738
+ result.push(ops[i]);
42739
+ i++;
42740
+ }
42741
+ return result;
42742
+ }
42513
42743
  function asInteger(expr2) {
42514
42744
  if (isNumber(expr2)) {
42515
42745
  const n = expr2.re;
@@ -43513,7 +43743,21 @@ ${e.message}
43513
43743
  },
43514
43744
  Text: {
43515
43745
  description: "A sequence of strings, annotated expressions and other Text expressions",
43516
- signature: "(any*) -> expression"
43746
+ signature: "(any*) -> string",
43747
+ evaluate: (ops, { engine: ce }) => {
43748
+ if (ops.length === 0) return ce.string("");
43749
+ const parts = [];
43750
+ for (const op of ops) {
43751
+ const unwrapped = op.operator === "Annotated" ? op.op1 : op;
43752
+ if (isString(unwrapped)) parts.push(unwrapped.string);
43753
+ else {
43754
+ const evaluated = unwrapped.evaluate();
43755
+ if (isString(evaluated)) parts.push(evaluated.string);
43756
+ else parts.push(evaluated.toString());
43757
+ }
43758
+ }
43759
+ return ce.string(parts.join(""));
43760
+ }
43517
43761
  }
43518
43762
  },
43519
43763
  {
@@ -43608,7 +43852,16 @@ ${e.message}
43608
43852
  if (!isSymbol2(symbol2)) {
43609
43853
  symbol2 = checkType(ce, lhs, "symbol");
43610
43854
  }
43611
- return ce._fn("Assign", [symbol2, args[1].canonical]);
43855
+ const canonRhs = args[1].canonical;
43856
+ const result = ce._fn("Assign", [symbol2, canonRhs]);
43857
+ const symbolName2 = sym(symbol2);
43858
+ if (symbolName2 && isFunction2(canonRhs, "Function")) {
43859
+ if (!ce.lookupDefinition(symbolName2)) ce.symbol(symbolName2);
43860
+ const def = ce.lookupDefinition(symbolName2);
43861
+ if (def && isValueDef(def) && def.value.inferredType)
43862
+ def.value.type = ce.type("function");
43863
+ }
43864
+ return result;
43612
43865
  },
43613
43866
  evaluate: ([op1, op2], { engine: ce }) => {
43614
43867
  if (isFunction2(op1, "Subscript") && sym(op1.op1)) {
@@ -43805,6 +44058,7 @@ ${e.message}
43805
44058
  description: "Simplify an expression.",
43806
44059
  lazy: true,
43807
44060
  signature: "(any) -> expression",
44061
+ type: ([x]) => x?.type ?? void 0,
43808
44062
  canonical: (ops, { engine: ce }) => ce._fn("Simplify", checkArity(ce, ops, 1)),
43809
44063
  evaluate: ([x]) => x.simplify() ?? void 0
43810
44064
  },
@@ -54028,8 +54282,11 @@ Error in definition of "${name}"`,
54028
54282
  for (const local of locals) {
54029
54283
  for (const arg of args) {
54030
54284
  if (isFunction2(arg, "Assign") && isSymbol2(arg.ops[0], local)) {
54031
- if (_BaseCompiler.isComplexValued(arg.ops[1])) {
54285
+ const rhs = arg.ops[1];
54286
+ if (_BaseCompiler.isComplexValued(rhs)) {
54032
54287
  typeHints[local] = isWGSL ? "vec2f" : "vec2";
54288
+ } else if (_BaseCompiler.isIntegerValued(rhs)) {
54289
+ typeHints[local] = isWGSL ? "i32" : "int";
54033
54290
  }
54034
54291
  break;
54035
54292
  }
@@ -54234,12 +54491,9 @@ Error in definition of "${name}"`,
54234
54491
  /**
54235
54492
  * Determine at compile time whether an expression produces a complex value.
54236
54493
  *
54237
- * Rules:
54238
- * - Numbers: complex if im !== 0
54239
- * - Symbols: ImaginaryUnit is complex; others use expr.isReal
54240
- * (undefined is treated as real -- assume-real policy)
54241
- * - Functions: Abs, Arg, Re, Im always return real.
54242
- * All others: complex if any operand is complex.
54494
+ * Uses the expression's declared type (from operator signatures) when
54495
+ * available. Falls back to operand inspection for functions whose
54496
+ * return type is unknown.
54243
54497
  */
54244
54498
  static isComplexValued(expr2) {
54245
54499
  if (isNumber(expr2)) return expr2.im !== 0;
@@ -54250,13 +54504,24 @@ Error in definition of "${name}"`,
54250
54504
  return t.matches("complex") && !t.matches("real");
54251
54505
  }
54252
54506
  if (isFunction2(expr2)) {
54253
- const op = expr2.operator;
54254
- if (op === "Abs" || op === "Arg" || op === "Re" || op === "Im")
54255
- return false;
54507
+ const t = expr2.type;
54508
+ if (t.matches("complex") && !t.matches("real")) return true;
54509
+ if (t.matches("real")) return false;
54256
54510
  return expr2.ops.some((arg) => _BaseCompiler.isComplexValued(arg));
54257
54511
  }
54258
54512
  return false;
54259
54513
  }
54514
+ /** True if the expression is provably integer-typed. */
54515
+ static isIntegerValued(expr2) {
54516
+ if (isNumber(expr2)) return expr2.im === 0 && Number.isInteger(expr2.re);
54517
+ const t = expr2.type;
54518
+ return t ? t.matches("integer") : false;
54519
+ }
54520
+ /** True if the expression is provably non-negative (sign ≥ 0). */
54521
+ static isNonNegative(expr2) {
54522
+ if (isNumber(expr2)) return expr2.im === 0 && expr2.re >= 0;
54523
+ return expr2.isNonNegative === true;
54524
+ }
54260
54525
  /**
54261
54526
  * Generate a temporary variable name
54262
54527
  */
@@ -54510,14 +54775,27 @@ Error in definition of "${name}"`,
54510
54775
  } catch (e) {
54511
54776
  if (options?.fallback ?? true) {
54512
54777
  console.warn(
54513
- `Compilation fallback for "${expr2.operator}": ${e.message}`
54778
+ `Compilation fallback for "${expr2.operator}" (target: ${options?.to ?? "javascript"}): ${e.message}`
54514
54779
  );
54780
+ const ce = expr2.engine;
54781
+ const fallbackRun = ((vars) => {
54782
+ ce.pushScope();
54783
+ try {
54784
+ if (vars && typeof vars === "object") {
54785
+ for (const [k, v] of Object.entries(vars))
54786
+ ce.assign(k, v);
54787
+ }
54788
+ return expr2.evaluate().re;
54789
+ } finally {
54790
+ ce.popScope();
54791
+ }
54792
+ });
54515
54793
  return {
54516
54794
  target: options?.to ?? "javascript",
54517
54795
  success: false,
54518
54796
  code: "",
54519
54797
  calling: "expression",
54520
- run: applicableN1(expr2)
54798
+ run: fallbackRun
54521
54799
  };
54522
54800
  }
54523
54801
  throw e;
@@ -59667,6 +59945,86 @@ Error in definition of "${name}"`,
59667
59945
  for (const symbol2 of Object.values(commonSymbols)) symbol2?.reset();
59668
59946
  }
59669
59947
 
59948
+ // src/compute-engine/compilation/constant-folding.ts
59949
+ function formatFloat(n) {
59950
+ const str = n.toString();
59951
+ if (!str.includes(".") && !str.includes("e") && !str.includes("E")) {
59952
+ return `${str}.0`;
59953
+ }
59954
+ return str;
59955
+ }
59956
+ function tryGetConstant(expr2) {
59957
+ if (!isNumber(expr2)) return void 0;
59958
+ if (expr2.im !== 0) return void 0;
59959
+ const re = expr2.re;
59960
+ if (!isFinite(re)) return void 0;
59961
+ return re;
59962
+ }
59963
+ var NUMERIC_LITERAL_RE = /^-?\d+(\.\d+)?$/;
59964
+ function foldTerms(terms, identity, op) {
59965
+ const identityValue = op === "+" ? 0 : 1;
59966
+ let numericAcc = null;
59967
+ const symbolic = [];
59968
+ for (const term of terms) {
59969
+ if (NUMERIC_LITERAL_RE.test(term)) {
59970
+ const val = parseFloat(term);
59971
+ if (op === "*" && val === 0) return "0.0";
59972
+ if (numericAcc === null) {
59973
+ numericAcc = val;
59974
+ } else {
59975
+ numericAcc = op === "+" ? numericAcc + val : numericAcc * val;
59976
+ }
59977
+ } else {
59978
+ symbolic.push(term);
59979
+ }
59980
+ }
59981
+ if (numericAcc !== null && numericAcc !== identityValue) {
59982
+ symbolic.unshift(formatFloat(numericAcc));
59983
+ }
59984
+ if (symbolic.length === 0) {
59985
+ if (numericAcc !== null) return formatFloat(numericAcc);
59986
+ return identity;
59987
+ }
59988
+ if (symbolic.length === 1) return symbolic[0];
59989
+ return symbolic.join(op === "+" ? " + " : " * ");
59990
+ }
59991
+ function tryGetComplexParts(expr2, compile3) {
59992
+ if (isSymbol2(expr2, "ImaginaryUnit")) {
59993
+ return { re: null, im: "1.0" };
59994
+ }
59995
+ if (isNumber(expr2) && expr2.im !== 0) {
59996
+ const re = expr2.re;
59997
+ const im = expr2.im;
59998
+ return {
59999
+ re: re !== 0 ? formatFloat(re) : null,
60000
+ im: formatFloat(im)
60001
+ };
60002
+ }
60003
+ if (isFunction2(expr2, "Multiply")) {
60004
+ const ops = expr2.ops;
60005
+ const iIndex = ops.findIndex(
60006
+ (op) => isSymbol2(op, "ImaginaryUnit") || isNumber(op) && op.re === 0 && op.im !== 0
60007
+ );
60008
+ if (iIndex >= 0) {
60009
+ const iFactor = ops[iIndex];
60010
+ const iScale = isSymbol2(iFactor, "ImaginaryUnit") ? 1 : iFactor.im;
60011
+ const remaining = ops.filter((_, idx) => idx !== iIndex);
60012
+ if (remaining.length === 0) {
60013
+ return { re: null, im: formatFloat(iScale) };
60014
+ }
60015
+ const compiledFactors = remaining.map((r) => compile3(r));
60016
+ if (iScale !== 1)
60017
+ compiledFactors.unshift(formatFloat(iScale));
60018
+ const imCode = foldTerms(compiledFactors, "1.0", "*");
60019
+ return { re: null, im: imCode };
60020
+ }
60021
+ }
60022
+ if (BaseCompiler.isComplexValued(expr2)) {
60023
+ return null;
60024
+ }
60025
+ return { re: compile3(expr2), im: null };
60026
+ }
60027
+
59670
60028
  // src/compute-engine/compilation/javascript-target.ts
59671
60029
  var JAVASCRIPT_OPERATORS = {
59672
60030
  Add: ["+", 11],
@@ -59690,12 +60048,21 @@ Error in definition of "${name}"`,
59690
60048
  Abs: (args, compile3) => {
59691
60049
  if (BaseCompiler.isComplexValued(args[0]))
59692
60050
  return `_SYS.cabs(${compile3(args[0])})`;
60051
+ if (BaseCompiler.isNonNegative(args[0])) return compile3(args[0]);
59693
60052
  return `Math.abs(${compile3(args[0])})`;
59694
60053
  },
59695
60054
  Add: (args, compile3) => {
59696
60055
  if (args.length === 1) return compile3(args[0]);
59697
60056
  const anyComplex = args.some((a) => BaseCompiler.isComplexValued(a));
59698
- if (!anyComplex) return `(${args.map((x) => compile3(x)).join(" + ")})`;
60057
+ if (!anyComplex) {
60058
+ const constants = args.map(tryGetConstant);
60059
+ if (constants.every((c) => c !== void 0))
60060
+ return String(constants.reduce((a, b) => a + b, 0));
60061
+ const nonZero = args.filter((a) => tryGetConstant(a) !== 0);
60062
+ if (nonZero.length === 0) return "0";
60063
+ if (nonZero.length === 1) return compile3(nonZero[0]);
60064
+ return `(${nonZero.map((x) => compile3(x)).join(" + ")})`;
60065
+ }
59699
60066
  const parts = args.map((a) => {
59700
60067
  const code = compile3(a);
59701
60068
  return { code, isComplex: BaseCompiler.isComplexValued(a) };
@@ -59752,7 +60119,10 @@ Error in definition of "${name}"`,
59752
60119
  return `Math.atan(${compile3(args[0])})`;
59753
60120
  },
59754
60121
  Artanh: "Math.atanh",
59755
- Ceil: "Math.ceil",
60122
+ Ceil: (args, compile3) => {
60123
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
60124
+ return `Math.ceil(${compile3(args[0])})`;
60125
+ },
59756
60126
  Chop: "_SYS.chop",
59757
60127
  Cos: (args, compile3) => {
59758
60128
  if (BaseCompiler.isComplexValued(args[0]))
@@ -59795,7 +60165,10 @@ Error in definition of "${name}"`,
59795
60165
  return `_SYS.cexp(${compile3(args[0])})`;
59796
60166
  return `Math.exp(${compile3(args[0])})`;
59797
60167
  },
59798
- Floor: "Math.floor",
60168
+ Floor: (args, compile3) => {
60169
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
60170
+ return `Math.floor(${compile3(args[0])})`;
60171
+ },
59799
60172
  Fract: ([x], compile3) => {
59800
60173
  if (x === null) throw new Error("Fract: no argument");
59801
60174
  return BaseCompiler.inlineExpression("${x} - Math.floor(${x})", compile3(x));
@@ -59891,12 +60264,20 @@ Error in definition of "${name}"`,
59891
60264
  if (BaseCompiler.isComplexValued(base) || BaseCompiler.isComplexValued(exp3)) {
59892
60265
  return `_SYS.cpow(${compile3(base)}, ${compile3(exp3)})`;
59893
60266
  }
59894
- const expVal = exp3.re;
59895
- if (expVal === 0.5) return `Math.sqrt(${compile3(base)})`;
59896
- if (expVal === 1 / 3) return `Math.cbrt(${compile3(base)})`;
59897
- if (expVal === 1) return compile3(base);
59898
- if (expVal === -1) return `(1 / (${compile3(base)}))`;
59899
- if (expVal === -0.5) return `(1 / Math.sqrt(${compile3(base)}))`;
60267
+ const bConst = tryGetConstant(base);
60268
+ const eConst = tryGetConstant(exp3);
60269
+ if (bConst !== void 0 && eConst !== void 0)
60270
+ return String(Math.pow(bConst, eConst));
60271
+ if (eConst === 0) return "1";
60272
+ if (eConst === 1) return compile3(base);
60273
+ if (eConst === 2 && (isSymbol2(base) || isNumber(base))) {
60274
+ const code = compile3(base);
60275
+ return `(${code} * ${code})`;
60276
+ }
60277
+ if (eConst === -1) return `(1 / (${compile3(base)}))`;
60278
+ if (eConst === 0.5) return `Math.sqrt(${compile3(base)})`;
60279
+ if (eConst === 1 / 3) return `Math.cbrt(${compile3(base)})`;
60280
+ if (eConst === -0.5) return `(1 / Math.sqrt(${compile3(base)}))`;
59900
60281
  return `Math.pow(${compile3(base)}, ${compile3(exp3)})`;
59901
60282
  },
59902
60283
  Range: (args, compile3) => {
@@ -59933,16 +60314,29 @@ Error in definition of "${name}"`,
59933
60314
  Root: ([arg, exp3], compile3) => {
59934
60315
  if (arg === null) throw new Error("Root: no argument");
59935
60316
  if (exp3 === null) return `Math.sqrt(${compile3(arg)})`;
59936
- if (exp3?.re === 2) return `Math.sqrt(${compile3(arg)})`;
59937
- if (exp3?.re === 3) return `Math.cbrt(${compile3(arg)})`;
59938
- if (!isNaN(exp3?.re)) return `Math.pow(${compile3(arg)}, ${1 / exp3.re})`;
60317
+ const aConst = tryGetConstant(arg);
60318
+ const nConst = tryGetConstant(exp3);
60319
+ if (aConst !== void 0 && nConst !== void 0 && nConst !== 0)
60320
+ return String(Math.pow(aConst, 1 / nConst));
60321
+ if (nConst === 2) return `Math.sqrt(${compile3(arg)})`;
60322
+ if (nConst === 3) return `Math.cbrt(${compile3(arg)})`;
60323
+ if (nConst !== void 0) return `Math.pow(${compile3(arg)}, ${1 / nConst})`;
59939
60324
  return `Math.pow(${compile3(arg)}, 1 / (${compile3(exp3)}))`;
59940
60325
  },
59941
60326
  Random: "Math.random",
59942
- Round: "Math.round",
60327
+ Round: (args, compile3) => {
60328
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
60329
+ return `Math.round(${compile3(args[0])})`;
60330
+ },
59943
60331
  Square: (args, compile3) => {
59944
60332
  const arg = args[0];
59945
60333
  if (arg === null) throw new Error("Square: no argument");
60334
+ const c = tryGetConstant(arg);
60335
+ if (c !== void 0) return String(c * c);
60336
+ if (isSymbol2(arg)) {
60337
+ const code = compile3(arg);
60338
+ return `(${code} * ${code})`;
60339
+ }
59946
60340
  return `Math.pow(${compile3(arg)}, 2)`;
59947
60341
  },
59948
60342
  Sec: (args, compile3) => {
@@ -59975,6 +60369,8 @@ Error in definition of "${name}"`,
59975
60369
  Sqrt: (args, compile3) => {
59976
60370
  if (BaseCompiler.isComplexValued(args[0]))
59977
60371
  return `_SYS.csqrt(${compile3(args[0])})`;
60372
+ const c = tryGetConstant(args[0]);
60373
+ if (c !== void 0) return String(Math.sqrt(c));
59978
60374
  return `Math.sqrt(${compile3(args[0])})`;
59979
60375
  },
59980
60376
  Tan: (args, compile3) => {
@@ -59991,9 +60387,14 @@ Error in definition of "${name}"`,
59991
60387
  if (a === null || b === null) throw new Error("Mod: missing argument");
59992
60388
  const ca = compile3(a);
59993
60389
  const cb = compile3(b);
60390
+ if (BaseCompiler.isIntegerValued(a) && BaseCompiler.isIntegerValued(b) && BaseCompiler.isNonNegative(a))
60391
+ return `(${ca} % ${cb})`;
59994
60392
  return `((${ca} % ${cb}) + ${cb}) % ${cb}`;
59995
60393
  },
59996
- Truncate: "Math.trunc",
60394
+ Truncate: (args, compile3) => {
60395
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
60396
+ return `Math.trunc(${compile3(args[0])})`;
60397
+ },
59997
60398
  Remainder: ([a, b], compile3) => {
59998
60399
  if (a === null || b === null)
59999
60400
  throw new Error("Remainder: missing argument");
@@ -60001,25 +60402,20 @@ Error in definition of "${name}"`,
60001
60402
  a
60002
60403
  )} / ${compile3(b)}))`;
60003
60404
  },
60004
- // Arithmetic operators handled as functions for completeness
60005
- Subtract: ([a, b], compile3) => {
60006
- if (a === null || b === null) throw new Error("Subtract: missing argument");
60007
- const ac = BaseCompiler.isComplexValued(a);
60008
- const bc = BaseCompiler.isComplexValued(b);
60009
- if (!ac && !bc) return `(${compile3(a)} - ${compile3(b)})`;
60010
- const ca = compile3(a);
60011
- const cb = compile3(b);
60012
- const reA = ac ? `(${ca}).re` : ca;
60013
- const imA = ac ? `(${ca}).im` : "0";
60014
- const reB = bc ? `(${cb}).re` : cb;
60015
- const imB = bc ? `(${cb}).im` : "0";
60016
- return `({ re: ${reA} - ${reB}, im: ${imA} - ${imB} })`;
60017
- },
60405
+ // No Subtract function handler Subtract canonicalizes to Add+Negate.
60406
+ // The operator entry in JAVASCRIPT_OPERATORS handles any edge cases.
60018
60407
  Divide: ([a, b], compile3) => {
60019
60408
  if (a === null || b === null) throw new Error("Divide: missing argument");
60020
60409
  const ac = BaseCompiler.isComplexValued(a);
60021
60410
  const bc = BaseCompiler.isComplexValued(b);
60022
- if (!ac && !bc) return `(${compile3(a)} / ${compile3(b)})`;
60411
+ if (!ac && !bc) {
60412
+ const ca = tryGetConstant(a);
60413
+ const cb = tryGetConstant(b);
60414
+ if (ca !== void 0 && cb !== void 0 && cb !== 0)
60415
+ return String(ca / cb);
60416
+ if (cb === 1) return compile3(a);
60417
+ return `(${compile3(a)} / ${compile3(b)})`;
60418
+ }
60023
60419
  if (ac && bc) {
60024
60420
  return `(() => { const _a = ${compile3(a)}, _b = ${compile3(
60025
60421
  b
@@ -60036,13 +60432,26 @@ Error in definition of "${name}"`,
60036
60432
  },
60037
60433
  Negate: ([x], compile3) => {
60038
60434
  if (x === null) throw new Error("Negate: no argument");
60039
- if (!BaseCompiler.isComplexValued(x)) return `(-${compile3(x)})`;
60435
+ if (!BaseCompiler.isComplexValued(x)) {
60436
+ const c = tryGetConstant(x);
60437
+ if (c !== void 0) return String(-c);
60438
+ return `(-${compile3(x)})`;
60439
+ }
60040
60440
  return `_SYS.cneg(${compile3(x)})`;
60041
60441
  },
60042
60442
  Multiply: (args, compile3) => {
60043
60443
  if (args.length === 1) return compile3(args[0]);
60044
60444
  const anyComplex = args.some((a) => BaseCompiler.isComplexValued(a));
60045
- if (!anyComplex) return `(${args.map((x) => compile3(x)).join(" * ")})`;
60445
+ if (!anyComplex) {
60446
+ if (args.some((a) => tryGetConstant(a) === 0)) return "0";
60447
+ const constants = args.map(tryGetConstant);
60448
+ if (constants.every((c) => c !== void 0))
60449
+ return String(constants.reduce((a, b) => a * b, 1));
60450
+ const nonOne = args.filter((a) => tryGetConstant(a) !== 1);
60451
+ if (nonOne.length === 0) return "1";
60452
+ if (nonOne.length === 1) return compile3(nonOne[0]);
60453
+ return `(${nonOne.map((x) => compile3(x)).join(" * ")})`;
60454
+ }
60046
60455
  if (args.length === 2) {
60047
60456
  const ac = BaseCompiler.isComplexValued(args[0]);
60048
60457
  const bc = BaseCompiler.isComplexValued(args[1]);
@@ -60127,20 +60536,30 @@ Error in definition of "${name}"`,
60127
60536
  AiryAi: "_SYS.airyAi",
60128
60537
  AiryBi: "_SYS.airyBi",
60129
60538
  // Combinatorics
60539
+ Mandelbrot: ([c, maxIter], compile3) => {
60540
+ if (c === null || maxIter === null)
60541
+ throw new Error("Mandelbrot: missing arguments");
60542
+ return `_SYS.mandelbrot(${compile3(c)}, ${compile3(maxIter)})`;
60543
+ },
60544
+ Julia: ([z, c, maxIter], compile3) => {
60545
+ if (z === null || c === null || maxIter === null)
60546
+ throw new Error("Julia: missing arguments");
60547
+ return `_SYS.julia(${compile3(z)}, ${compile3(c)}, ${compile3(maxIter)})`;
60548
+ },
60130
60549
  Binomial: (args, compile3) => `_SYS.binomial(${compile3(args[0])}, ${compile3(args[1])})`,
60131
60550
  Fibonacci: "_SYS.fibonacci",
60132
60551
  // Complex-specific functions
60133
- Re: (args, compile3) => {
60552
+ Real: (args, compile3) => {
60134
60553
  if (BaseCompiler.isComplexValued(args[0]))
60135
60554
  return `(${compile3(args[0])}).re`;
60136
60555
  return compile3(args[0]);
60137
60556
  },
60138
- Im: (args, compile3) => {
60557
+ Imaginary: (args, compile3) => {
60139
60558
  if (BaseCompiler.isComplexValued(args[0]))
60140
60559
  return `(${compile3(args[0])}).im`;
60141
60560
  return "0";
60142
60561
  },
60143
- Arg: (args, compile3) => {
60562
+ Argument: (args, compile3) => {
60144
60563
  if (BaseCompiler.isComplexValued(args[0]))
60145
60564
  return `_SYS.carg(${compile3(args[0])})`;
60146
60565
  return `(${compile3(args[0])} >= 0 ? 0 : Math.PI)`;
@@ -60476,6 +60895,41 @@ Error in definition of "${name}"`,
60476
60895
  sinc,
60477
60896
  fresnelS,
60478
60897
  fresnelC,
60898
+ mandelbrot: (c, maxIter) => {
60899
+ let zx = 0, zy = 0;
60900
+ const cx = typeof c === "number" ? c : c.re;
60901
+ const cy = typeof c === "number" ? 0 : c.im;
60902
+ const n = Math.round(maxIter);
60903
+ for (let i = 0; i < n; i++) {
60904
+ const newZx = zx * zx - zy * zy + cx;
60905
+ zy = 2 * zx * zy + cy;
60906
+ zx = newZx;
60907
+ const mag2 = zx * zx + zy * zy;
60908
+ if (mag2 > 4) {
60909
+ const smooth = (i - Math.log2(Math.log2(mag2)) + 4) / n;
60910
+ return Math.max(0, Math.min(1, smooth));
60911
+ }
60912
+ }
60913
+ return 1;
60914
+ },
60915
+ julia: (z, c, maxIter) => {
60916
+ let zx = typeof z === "number" ? z : z.re;
60917
+ let zy = typeof z === "number" ? 0 : z.im;
60918
+ const cx = typeof c === "number" ? c : c.re;
60919
+ const cy = typeof c === "number" ? 0 : c.im;
60920
+ const n = Math.round(maxIter);
60921
+ for (let i = 0; i < n; i++) {
60922
+ const newZx = zx * zx - zy * zy + cx;
60923
+ zy = 2 * zx * zy + cy;
60924
+ zx = newZx;
60925
+ const mag2 = zx * zx + zy * zy;
60926
+ if (mag2 > 4) {
60927
+ const smooth = (i - Math.log2(Math.log2(mag2)) + 4) / n;
60928
+ return Math.max(0, Math.min(1, smooth));
60929
+ }
60930
+ }
60931
+ return 1;
60932
+ },
60479
60933
  binomial: choose,
60480
60934
  fibonacci,
60481
60935
  // Complex helpers
@@ -60821,6 +61275,7 @@ Error in definition of "${name}"`,
60821
61275
  Add: ["+", 11],
60822
61276
  Negate: ["-", 14],
60823
61277
  Subtract: ["-", 11],
61278
+ // Subtract canonicalizes to Add+Negate; kept as fallback
60824
61279
  Multiply: ["*", 12],
60825
61280
  Divide: ["/", 13],
60826
61281
  Equal: ["==", 8],
@@ -60836,6 +61291,12 @@ Error in definition of "${name}"`,
60836
61291
  function gpuVec2(target) {
60837
61292
  return target?.language === "wgsl" ? "vec2f" : "vec2";
60838
61293
  }
61294
+ function compileIntArg(expr2, compile3, target) {
61295
+ const c = tryGetConstant(expr2);
61296
+ if (c !== void 0 && Number.isInteger(c)) return c.toString();
61297
+ const intCast = target?.language === "wgsl" ? "i32" : "int";
61298
+ return `${intCast}(${compile3(expr2)})`;
61299
+ }
60839
61300
  var GPU_UNROLL_LIMIT = 100;
60840
61301
  function compileGPUSumProduct(kind, args, _compile2, target) {
60841
61302
  if (!args[0]) throw new Error(`${kind}: no body`);
@@ -60898,88 +61359,113 @@ Error in definition of "${name}"`,
60898
61359
  if (args.length === 0) return "0.0";
60899
61360
  if (args.length === 1) return compile3(args[0]);
60900
61361
  const anyComplex = args.some((a) => BaseCompiler.isComplexValued(a));
60901
- if (!anyComplex) return args.map((x) => compile3(x)).join(" + ");
60902
- const v2 = gpuVec2(target);
60903
- return args.map((a) => {
60904
- const code = compile3(a);
60905
- return BaseCompiler.isComplexValued(a) ? code : `${v2}(${code}, 0.0)`;
60906
- }).join(" + ");
60907
- },
60908
- Multiply: (args, compile3, _target) => {
60909
- if (args.length === 0) return "1.0";
60910
- if (args.length === 1) return compile3(args[0]);
60911
- const anyComplex = args.some((a) => BaseCompiler.isComplexValued(a));
60912
- if (!anyComplex) return args.map((x) => compile3(x)).join(" * ");
60913
- let result = compile3(args[0]);
60914
- let resultIsComplex = BaseCompiler.isComplexValued(args[0]);
60915
- for (let i = 1; i < args.length; i++) {
60916
- const code = compile3(args[i]);
60917
- const argIsComplex = BaseCompiler.isComplexValued(args[i]);
60918
- if (!resultIsComplex && !argIsComplex) {
60919
- result = `(${result} * ${code})`;
60920
- } else if (resultIsComplex && !argIsComplex) {
60921
- result = `(${code} * ${result})`;
60922
- } else if (!resultIsComplex && argIsComplex) {
60923
- result = `(${result} * ${code})`;
60924
- resultIsComplex = true;
60925
- } else {
60926
- result = `_gpu_cmul(${result}, ${code})`;
60927
- }
61362
+ if (!anyComplex) {
61363
+ return foldTerms(
61364
+ args.map((x) => compile3(x)),
61365
+ "0.0",
61366
+ "+"
61367
+ );
60928
61368
  }
60929
- return result;
60930
- },
60931
- Subtract: (args, compile3, target) => {
60932
- if (args.length === 0) return "0.0";
61369
+ const parts = args.map((a) => tryGetComplexParts(a, compile3));
61370
+ if (parts.some((p) => p === null)) {
61371
+ const v2 = gpuVec2(target);
61372
+ return args.map((a) => {
61373
+ const code = compile3(a);
61374
+ return BaseCompiler.isComplexValued(a) ? code : `${v2}(${code}, 0.0)`;
61375
+ }).join(" + ");
61376
+ }
61377
+ const reParts = [];
61378
+ const imParts = [];
61379
+ for (const p of parts) {
61380
+ if (p.re !== null) reParts.push(p.re);
61381
+ if (p.im !== null) imParts.push(p.im);
61382
+ }
61383
+ const reSum = foldTerms(reParts, "0.0", "+");
61384
+ const imSum = foldTerms(imParts, "0.0", "+");
61385
+ return `${gpuVec2(target)}(${reSum}, ${imSum})`;
61386
+ },
61387
+ Multiply: (args, compile3, target) => {
61388
+ if (args.length === 0) return "1.0";
60933
61389
  if (args.length === 1) return compile3(args[0]);
60934
61390
  const anyComplex = args.some((a) => BaseCompiler.isComplexValued(a));
60935
61391
  if (!anyComplex) {
60936
- if (args.length === 2) return `${compile3(args[0])} - ${compile3(args[1])}`;
60937
- let result2 = compile3(args[0]);
60938
- for (let i = 1; i < args.length; i++) {
60939
- result2 = `${result2} - ${compile3(args[i])}`;
60940
- }
60941
- return result2;
60942
- }
60943
- const v2 = gpuVec2(target);
60944
- const promote = (a) => {
60945
- const code = compile3(a);
60946
- return BaseCompiler.isComplexValued(a) ? code : `${v2}(${code}, 0.0)`;
60947
- };
60948
- if (args.length === 2) return `${promote(args[0])} - ${promote(args[1])}`;
60949
- let result = promote(args[0]);
60950
- for (let i = 1; i < args.length; i++) {
60951
- result = `${result} - ${promote(args[i])}`;
61392
+ return foldTerms(
61393
+ args.map((x) => compile3(x)),
61394
+ "1.0",
61395
+ "*"
61396
+ );
60952
61397
  }
61398
+ const iIndex = args.findIndex(
61399
+ (op) => isSymbol2(op, "ImaginaryUnit") || isNumber(op) && op.re === 0 && op.im !== 0
61400
+ );
61401
+ if (iIndex >= 0) {
61402
+ const iFactor = args[iIndex];
61403
+ const iScale = isSymbol2(iFactor, "ImaginaryUnit") ? 1 : iFactor.im;
61404
+ const realFactors = args.filter((_, i) => i !== iIndex);
61405
+ const v2 = gpuVec2(target);
61406
+ if (realFactors.length === 0)
61407
+ return `${v2}(0.0, ${formatFloat(iScale)})`;
61408
+ const factors = realFactors.map((f) => compile3(f));
61409
+ if (iScale !== 1) factors.unshift(formatFloat(iScale));
61410
+ const imCode = foldTerms(factors, "1.0", "*");
61411
+ return `${v2}(0.0, ${imCode})`;
61412
+ }
61413
+ const realCodes = [];
61414
+ const complexCodes = [];
61415
+ for (const a of args) {
61416
+ if (BaseCompiler.isComplexValued(a)) complexCodes.push(compile3(a));
61417
+ else realCodes.push(compile3(a));
61418
+ }
61419
+ const scalarCode = foldTerms(realCodes, "1.0", "*");
61420
+ let result = complexCodes[0];
61421
+ for (let i = 1; i < complexCodes.length; i++) {
61422
+ result = `_gpu_cmul(${result}, ${complexCodes[i]})`;
61423
+ }
61424
+ if (scalarCode !== "1.0") result = `(${scalarCode} * ${result})`;
60953
61425
  return result;
60954
61426
  },
61427
+ // No Subtract function handler — Subtract canonicalizes to Add+Negate.
61428
+ // The operator entry in GPU_OPERATORS handles any edge cases.
60955
61429
  Divide: (args, compile3, target) => {
60956
61430
  if (args.length === 0) return "1.0";
60957
61431
  if (args.length === 1) return compile3(args[0]);
60958
61432
  const ac = BaseCompiler.isComplexValued(args[0]);
60959
61433
  const bc = args.length >= 2 && BaseCompiler.isComplexValued(args[1]);
60960
61434
  if (!ac && !bc) {
60961
- if (args.length === 2) return `${compile3(args[0])} / ${compile3(args[1])}`;
61435
+ if (args.length === 2) {
61436
+ const a = tryGetConstant(args[0]);
61437
+ const b = tryGetConstant(args[1]);
61438
+ if (a !== void 0 && b !== void 0 && b !== 0)
61439
+ return formatFloat(a / b);
61440
+ if (b === 1) return compile3(args[0]);
61441
+ return `${compile3(args[0])} / ${compile3(args[1])}`;
61442
+ }
60962
61443
  let result = compile3(args[0]);
60963
- for (let i = 1; i < args.length; i++) {
61444
+ for (let i = 1; i < args.length; i++)
60964
61445
  result = `${result} / ${compile3(args[i])}`;
60965
- }
60966
61446
  return result;
60967
61447
  }
60968
61448
  if (ac && bc) return `_gpu_cdiv(${compile3(args[0])}, ${compile3(args[1])})`;
60969
- if (ac && !bc) {
60970
- return `(${compile3(args[0])} / ${compile3(args[1])})`;
60971
- }
61449
+ if (ac && !bc) return `(${compile3(args[0])} / ${compile3(args[1])})`;
60972
61450
  const v2 = gpuVec2(target);
60973
61451
  return `_gpu_cdiv(${v2}(${compile3(args[0])}, 0.0), ${compile3(args[1])})`;
60974
61452
  },
60975
- Negate: ([x], compile3) => {
61453
+ Negate: ([x], compile3, target) => {
60976
61454
  if (x === null) throw new Error("Negate: no argument");
61455
+ const c = tryGetConstant(x);
61456
+ if (c !== void 0) return formatFloat(-c);
61457
+ if (isNumber(x) && x.im !== 0) {
61458
+ return `${gpuVec2(target)}(${formatFloat(-x.re)}, ${formatFloat(-x.im)})`;
61459
+ }
61460
+ if (isSymbol2(x, "ImaginaryUnit"))
61461
+ return `${gpuVec2(target)}(0.0, -1.0)`;
60977
61462
  return `(-${compile3(x)})`;
60978
61463
  },
60979
61464
  // Standard math functions with complex dispatch
60980
61465
  Abs: (args, compile3) => {
60981
61466
  if (BaseCompiler.isComplexValued(args[0]))
60982
61467
  return `length(${compile3(args[0])})`;
61468
+ if (BaseCompiler.isNonNegative(args[0])) return compile3(args[0]);
60983
61469
  return `abs(${compile3(args[0])})`;
60984
61470
  },
60985
61471
  Arccos: (args, compile3) => {
@@ -60997,7 +61483,10 @@ Error in definition of "${name}"`,
60997
61483
  return `_gpu_catan(${compile3(args[0])})`;
60998
61484
  return `atan(${compile3(args[0])})`;
60999
61485
  },
61000
- Ceil: "ceil",
61486
+ Ceil: (args, compile3) => {
61487
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
61488
+ return `ceil(${compile3(args[0])})`;
61489
+ },
61001
61490
  Clamp: "clamp",
61002
61491
  Cos: (args, compile3) => {
61003
61492
  if (BaseCompiler.isComplexValued(args[0]))
@@ -61011,7 +61500,10 @@ Error in definition of "${name}"`,
61011
61500
  return `exp(${compile3(args[0])})`;
61012
61501
  },
61013
61502
  Exp2: "exp2",
61014
- Floor: "floor",
61503
+ Floor: (args, compile3) => {
61504
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
61505
+ return `floor(${compile3(args[0])})`;
61506
+ },
61015
61507
  Fract: "fract",
61016
61508
  Ln: (args, compile3) => {
61017
61509
  if (BaseCompiler.isComplexValued(args[0]))
@@ -61033,10 +61525,25 @@ Error in definition of "${name}"`,
61033
61525
  const eCode = BaseCompiler.isComplexValued(exp3) ? compile3(exp3) : `${v2}(${compile3(exp3)}, 0.0)`;
61034
61526
  return `_gpu_cpow(${bCode}, ${eCode})`;
61035
61527
  }
61528
+ const bConst = tryGetConstant(base);
61529
+ const eConst = tryGetConstant(exp3);
61530
+ if (bConst !== void 0 && eConst !== void 0)
61531
+ return formatFloat(Math.pow(bConst, eConst));
61532
+ if (eConst === 0) return "1.0";
61533
+ if (eConst === 1) return compile3(base);
61534
+ if (eConst === 2 && (isSymbol2(base) || isNumber(base))) {
61535
+ const code = compile3(base);
61536
+ return `(${code} * ${code})`;
61537
+ }
61538
+ if (eConst === -1) return `(1.0 / ${compile3(base)})`;
61539
+ if (eConst === 0.5) return `sqrt(${compile3(base)})`;
61036
61540
  return `pow(${compile3(base)}, ${compile3(exp3)})`;
61037
61541
  },
61038
61542
  Radians: "radians",
61039
- Round: "round",
61543
+ Round: (args, compile3) => {
61544
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
61545
+ return `round(${compile3(args[0])})`;
61546
+ },
61040
61547
  Sign: "sign",
61041
61548
  Sin: (args, compile3) => {
61042
61549
  if (BaseCompiler.isComplexValued(args[0]))
@@ -61047,6 +61554,8 @@ Error in definition of "${name}"`,
61047
61554
  Sqrt: (args, compile3) => {
61048
61555
  if (BaseCompiler.isComplexValued(args[0]))
61049
61556
  return `_gpu_csqrt(${compile3(args[0])})`;
61557
+ const c = tryGetConstant(args[0]);
61558
+ if (c !== void 0) return formatFloat(Math.sqrt(c));
61050
61559
  return `sqrt(${compile3(args[0])})`;
61051
61560
  },
61052
61561
  Step: "step",
@@ -61055,17 +61564,20 @@ Error in definition of "${name}"`,
61055
61564
  return `_gpu_ctan(${compile3(args[0])})`;
61056
61565
  return `tan(${compile3(args[0])})`;
61057
61566
  },
61058
- Truncate: "trunc",
61567
+ Truncate: (args, compile3) => {
61568
+ if (BaseCompiler.isIntegerValued(args[0])) return compile3(args[0]);
61569
+ return `trunc(${compile3(args[0])})`;
61570
+ },
61059
61571
  // Complex-specific functions
61060
- Re: (args, compile3) => {
61572
+ Real: (args, compile3) => {
61061
61573
  if (BaseCompiler.isComplexValued(args[0])) return `(${compile3(args[0])}).x`;
61062
61574
  return compile3(args[0]);
61063
61575
  },
61064
- Im: (args, compile3) => {
61576
+ Imaginary: (args, compile3) => {
61065
61577
  if (BaseCompiler.isComplexValued(args[0])) return `(${compile3(args[0])}).y`;
61066
61578
  return "0.0";
61067
61579
  },
61068
- Arg: (args, compile3) => {
61580
+ Argument: (args, compile3) => {
61069
61581
  if (BaseCompiler.isComplexValued(args[0])) {
61070
61582
  const code = compile3(args[0]);
61071
61583
  return `atan(${code}.y, ${code}.x)`;
@@ -61280,13 +61792,20 @@ Error in definition of "${name}"`,
61280
61792
  },
61281
61793
  Square: ([x], compile3) => {
61282
61794
  if (x === null) throw new Error("Square: no argument");
61283
- const arg = compile3(x);
61284
- return `(${arg} * ${arg})`;
61795
+ if (isSymbol2(x) || isNumber(x)) {
61796
+ const arg = compile3(x);
61797
+ return `(${arg} * ${arg})`;
61798
+ }
61799
+ return `pow(${compile3(x)}, 2.0)`;
61285
61800
  },
61286
61801
  Root: ([x, n], compile3) => {
61287
61802
  if (x === null) throw new Error("Root: no argument");
61288
61803
  if (n === null || n === void 0) return `sqrt(${compile3(x)})`;
61289
- if (n?.re === 2) return `sqrt(${compile3(x)})`;
61804
+ const nConst = tryGetConstant(n);
61805
+ if (nConst === 2) return `sqrt(${compile3(x)})`;
61806
+ const xConst = tryGetConstant(x);
61807
+ if (xConst !== void 0 && nConst !== void 0)
61808
+ return formatFloat(Math.pow(xConst, 1 / nConst));
61290
61809
  return `pow(${compile3(x)}, 1.0 / ${compile3(n)})`;
61291
61810
  },
61292
61811
  // Color functions (pure-math, GPU-compilable)
@@ -61328,18 +61847,14 @@ Error in definition of "${name}"`,
61328
61847
  Mandelbrot: ([c, maxIter], compile3, target) => {
61329
61848
  if (c === null || maxIter === null)
61330
61849
  throw new Error("Mandelbrot: missing arguments");
61331
- const intCast = target?.language === "wgsl" ? "i32" : "int";
61332
- return `_fractal_mandelbrot(${compile3(c)}, ${intCast}(${compile3(
61333
- maxIter
61334
- )}))`;
61850
+ const iterCode = compileIntArg(maxIter, compile3, target);
61851
+ return `_fractal_mandelbrot(${compile3(c)}, ${iterCode})`;
61335
61852
  },
61336
61853
  Julia: ([z, c, maxIter], compile3, target) => {
61337
61854
  if (z === null || c === null || maxIter === null)
61338
61855
  throw new Error("Julia: missing arguments");
61339
- const intCast = target?.language === "wgsl" ? "i32" : "int";
61340
- return `_fractal_julia(${compile3(z)}, ${compile3(c)}, ${intCast}(${compile3(
61341
- maxIter
61342
- )}))`;
61856
+ const iterCode = compileIntArg(maxIter, compile3, target);
61857
+ return `_fractal_julia(${compile3(z)}, ${compile3(c)}, ${iterCode})`;
61343
61858
  },
61344
61859
  // Vector/Matrix operations
61345
61860
  Cross: "cross",
@@ -63971,6 +64486,7 @@ ${workgroupAttr}fn main(${paramStr})${returnStr} {
63971
64486
  Add: ["_IA.add", 20],
63972
64487
  Negate: ["_IA.negate", 20],
63973
64488
  Subtract: ["_IA.sub", 20],
64489
+ // Subtract canonicalizes to Add+Negate; kept as fallback
63974
64490
  Multiply: ["_IA.mul", 20],
63975
64491
  Divide: ["_IA.div", 20],
63976
64492
  // Comparisons return BoolInterval
@@ -63995,17 +64511,7 @@ ${workgroupAttr}fn main(${paramStr})${returnStr} {
63995
64511
  }
63996
64512
  return result;
63997
64513
  },
63998
- Subtract: (args, compile3) => {
63999
- if (args.length === 0) return "_IA.point(0)";
64000
- if (args.length === 1) return `_IA.negate(${compile3(args[0])})`;
64001
- if (args.length === 2)
64002
- return `_IA.sub(${compile3(args[0])}, ${compile3(args[1])})`;
64003
- let result = compile3(args[0]);
64004
- for (let i = 1; i < args.length; i++) {
64005
- result = `_IA.sub(${result}, ${compile3(args[i])})`;
64006
- }
64007
- return result;
64008
- },
64514
+ // No Subtract handler canonicalizes to Add+Negate before compilation.
64009
64515
  Multiply: (args, compile3) => {
64010
64516
  if (args.length === 0) return "_IA.point(1)";
64011
64517
  if (args.length === 1) return compile3(args[0]);
@@ -66979,7 +67485,9 @@ ${workgroupAttr}fn main(${paramStr})${returnStr} {
66979
67485
  }
66980
67486
  return new ExactNumericValue(value, makeNumericValue);
66981
67487
  }
66982
- throw Error("Unexpected value");
67488
+ throw Error(
67489
+ `Unexpected value: ${typeof value === "object" ? JSON.stringify(value) : String(value)}`
67490
+ );
66983
67491
  }
66984
67492
  /**
66985
67493
  * The cost function is used to determine the "cost" of an expression. For example, when simplifying an expression, the simplification that results in the lowest cost is chosen.
@@ -67450,7 +67958,7 @@ ${workgroupAttr}fn main(${paramStr})${returnStr} {
67450
67958
  _setDefaultEngineFactory(() => new ComputeEngine());
67451
67959
 
67452
67960
  // src/core.ts
67453
- var version = "0.55.0";
67961
+ var version = "0.55.3";
67454
67962
  return __toCommonJS(core_exports);
67455
67963
  })();
67456
67964
  /*! Bundled license information: