plurimath 0.11.0 → 0.11.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 (120) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +3 -0
  3. data/.rubocop_todo.yml +311 -58
  4. data/Gemfile +3 -2
  5. data/README.adoc +331 -15
  6. data/lib/plurimath/asciimath/parse.rb +6 -1
  7. data/lib/plurimath/asciimath/transform.rb +2 -0
  8. data/lib/plurimath/base_number_prefix.rb +43 -0
  9. data/lib/plurimath/configuration.rb +9 -1
  10. data/lib/plurimath/deprecation.rb +2 -1
  11. data/lib/plurimath/errors/configuration_error.rb +5 -1
  12. data/lib/plurimath/errors/deprecation_error.rb +2 -1
  13. data/lib/plurimath/errors/evaluation/division_by_zero_error.rb +13 -0
  14. data/lib/plurimath/errors/evaluation/error.rb +9 -0
  15. data/lib/plurimath/errors/evaluation/invalid_binding_error.rb +14 -0
  16. data/lib/plurimath/errors/evaluation/invalid_binding_key_error.rb +14 -0
  17. data/lib/plurimath/errors/evaluation/math_domain_error.rb +9 -0
  18. data/lib/plurimath/errors/evaluation/missing_variable_error.rb +13 -0
  19. data/lib/plurimath/errors/evaluation/non_finite_result_error.rb +13 -0
  20. data/lib/plurimath/errors/evaluation/unsupported_expression_error.rb +13 -0
  21. data/lib/plurimath/errors/evaluation.rb +18 -0
  22. data/lib/plurimath/errors/invalid_number.rb +17 -0
  23. data/lib/plurimath/errors/unsupported_base.rb +18 -0
  24. data/lib/plurimath/errors/{formatter/unsupported_locale.rb → unsupported_locale.rb} +1 -1
  25. data/lib/plurimath/errors.rb +9 -0
  26. data/lib/plurimath/formatter/numbers/base_notation.rb +55 -27
  27. data/lib/plurimath/formatter/numbers/format_options.rb +123 -17
  28. data/lib/plurimath/formatter/numbers/formatted_notation.rb +62 -0
  29. data/lib/plurimath/formatter/numbers/formatted_number.rb +87 -0
  30. data/lib/plurimath/formatter/numbers/fraction.rb +8 -17
  31. data/lib/plurimath/formatter/numbers/integer.rb +3 -0
  32. data/lib/plurimath/formatter/numbers/mathml_renderer.rb +56 -0
  33. data/lib/plurimath/formatter/numbers/notation_renderer.rb +58 -28
  34. data/lib/plurimath/formatter/numbers/number_renderer.rb +26 -13
  35. data/lib/plurimath/formatter/numbers/omml_renderer.rb +74 -0
  36. data/lib/plurimath/formatter/numbers/precision_resolver.rb +16 -3
  37. data/lib/plurimath/formatter/numbers/sign_renderer.rb +2 -1
  38. data/lib/plurimath/formatter/numbers/significant.rb +4 -2
  39. data/lib/plurimath/formatter/numbers/source.rb +46 -6
  40. data/lib/plurimath/formatter/numbers/text_renderer.rb +52 -0
  41. data/lib/plurimath/formatter/numbers.rb +6 -2
  42. data/lib/plurimath/formatter/standard.rb +6 -0
  43. data/lib/plurimath/formatter/supported_locales.rb +1 -1
  44. data/lib/plurimath/formatter.rb +0 -2
  45. data/lib/plurimath/html/parse.rb +5 -0
  46. data/lib/plurimath/html/transform.rb +26 -12
  47. data/lib/plurimath/latex/parse.rb +5 -0
  48. data/lib/plurimath/latex/transform.rb +2 -0
  49. data/lib/plurimath/math/core.rb +69 -14
  50. data/lib/plurimath/math/evaluation/evaluator.rb +147 -0
  51. data/lib/plurimath/math/evaluation/expression_parser.rb +215 -0
  52. data/lib/plurimath/math/evaluation/iteration.rb +63 -0
  53. data/lib/plurimath/math/evaluation.rb +13 -0
  54. data/lib/plurimath/math/formula.rb +9 -0
  55. data/lib/plurimath/math/function/abs.rb +4 -0
  56. data/lib/plurimath/math/function/arccos.rb +4 -0
  57. data/lib/plurimath/math/function/arcsin.rb +4 -0
  58. data/lib/plurimath/math/function/arctan.rb +4 -0
  59. data/lib/plurimath/math/function/ceil.rb +4 -0
  60. data/lib/plurimath/math/function/cos.rb +4 -0
  61. data/lib/plurimath/math/function/cosh.rb +4 -0
  62. data/lib/plurimath/math/function/cot.rb +4 -0
  63. data/lib/plurimath/math/function/coth.rb +4 -0
  64. data/lib/plurimath/math/function/csc.rb +4 -0
  65. data/lib/plurimath/math/function/csch.rb +4 -0
  66. data/lib/plurimath/math/function/exp.rb +4 -0
  67. data/lib/plurimath/math/function/fenced.rb +4 -0
  68. data/lib/plurimath/math/function/floor.rb +4 -0
  69. data/lib/plurimath/math/function/frac.rb +7 -0
  70. data/lib/plurimath/math/function/gcd.rb +9 -0
  71. data/lib/plurimath/math/function/lcm.rb +9 -0
  72. data/lib/plurimath/math/function/lg.rb +4 -0
  73. data/lib/plurimath/math/function/ln.rb +4 -0
  74. data/lib/plurimath/math/function/log.rb +19 -0
  75. data/lib/plurimath/math/function/max.rb +4 -0
  76. data/lib/plurimath/math/function/min.rb +4 -0
  77. data/lib/plurimath/math/function/mod.rb +15 -0
  78. data/lib/plurimath/math/function/overleftrightarrow.rb +2 -2
  79. data/lib/plurimath/math/function/power.rb +10 -0
  80. data/lib/plurimath/math/function/prod.rb +10 -0
  81. data/lib/plurimath/math/function/root.rb +7 -0
  82. data/lib/plurimath/math/function/sec.rb +4 -0
  83. data/lib/plurimath/math/function/sech.rb +4 -0
  84. data/lib/plurimath/math/function/sin.rb +4 -0
  85. data/lib/plurimath/math/function/sinh.rb +4 -0
  86. data/lib/plurimath/math/function/sqrt.rb +4 -0
  87. data/lib/plurimath/math/function/sum.rb +10 -0
  88. data/lib/plurimath/math/function/tan.rb +4 -0
  89. data/lib/plurimath/math/function/tanh.rb +4 -0
  90. data/lib/plurimath/math/function/text.rb +17 -0
  91. data/lib/plurimath/math/number.rb +44 -23
  92. data/lib/plurimath/math/symbols/cdot.rb +4 -0
  93. data/lib/plurimath/math/symbols/div.rb +4 -0
  94. data/lib/plurimath/math/symbols/hat.rb +4 -0
  95. data/lib/plurimath/math/symbols/minus.rb +4 -0
  96. data/lib/plurimath/math/symbols/pi.rb +5 -1
  97. data/lib/plurimath/math/symbols/plus.rb +4 -0
  98. data/lib/plurimath/math/symbols/slash.rb +4 -0
  99. data/lib/plurimath/math/symbols/symbol.rb +45 -0
  100. data/lib/plurimath/math/symbols/times.rb +4 -0
  101. data/lib/plurimath/math.rb +5 -1
  102. data/lib/plurimath/mathml/constants.rb +18 -0
  103. data/lib/plurimath/number_formatter.rb +63 -3
  104. data/lib/plurimath/omml/formula_transformation.rb +2 -1
  105. data/lib/plurimath/omml/translator.rb +4 -1
  106. data/lib/plurimath/setup/opal.rb.erb +13 -0
  107. data/lib/plurimath/unicode_math/parse.rb +98 -54
  108. data/lib/plurimath/unicode_math/parser.rb +7 -4
  109. data/lib/plurimath/unicode_math/parsing_rules/absence_rules.rb +33 -21
  110. data/lib/plurimath/unicode_math/parsing_rules/common_rules.rb +28 -16
  111. data/lib/plurimath/unicode_math/parsing_rules/constants_rules.rb +18 -7
  112. data/lib/plurimath/unicode_math/parsing_rules/masked.rb +35 -15
  113. data/lib/plurimath/unicode_math/parsing_rules/sub_sup.rb +98 -72
  114. data/lib/plurimath/unicode_math/transform.rb +1 -0
  115. data/lib/plurimath/utility.rb +1 -1
  116. data/lib/plurimath/version.rb +1 -1
  117. data/lib/plurimath.rb +2 -0
  118. metadata +24 -5
  119. data/lib/plurimath/errors/formatter/unsupported_base.rb +0 -21
  120. data/lib/plurimath/formatter/numbers/parts_renderer.rb +0 -30
@@ -20,26 +20,52 @@ module Plurimath
20
20
 
21
21
  rule(:power_symbol) { str("^") }
22
22
  rule(:power_syntax) { power_symbol | above }
23
- rule(:sub_override) { (invisible_space? >> base_syntax >> op_size_overrides_symbols >> (operator_symbols.maybe >> baseless_sub_values(:sub_script))) }
24
- rule(:sup_override) { (invisible_space? >> power_syntax >> op_size_overrides_symbols >> (operator_symbols.maybe >> baseless_sup_values(:sup_script))) }
23
+ rule(:sub_override) do
24
+ invisible_space? >> base_syntax >> op_size_overrides_symbols >> (operator_symbols.maybe >> baseless_sub_values(:sub_script))
25
+ end
26
+ rule(:sup_override) do
27
+ invisible_space? >> power_syntax >> op_size_overrides_symbols >> (operator_symbols.maybe >> baseless_sup_values(:sup_script))
28
+ end
25
29
 
26
- rule(:sub_sup_paren) { sub_paren.as(:sub_paren) | sup_paren.as(:sup_paren) }
27
- rule(:pre_subscript) { base_syntax >> prescript_values.as(:pre_subscript) | sub_paren.as(:pre_subscript) }
28
- rule(:pre_supscript) { power_syntax >> prescript_values.as(:pre_supscript) | sup_paren.as(:pre_supscript) }
30
+ rule(:sub_sup_paren) do
31
+ sub_paren.as(:sub_paren) | sup_paren.as(:sup_paren)
32
+ end
33
+ rule(:pre_subscript) do
34
+ (base_syntax >> prescript_values.as(:pre_subscript)) | sub_paren.as(:pre_subscript)
35
+ end
36
+ rule(:pre_supscript) do
37
+ (power_syntax >> prescript_values.as(:pre_supscript)) | sup_paren.as(:pre_supscript)
38
+ end
29
39
 
30
- rule(:mini_sub_value) { (sub_sup_operand.as(:base) >> sub_paren.as(:sub)).as(:mini_sub) }
31
- rule(:mini_sup_value) { (sub_sup_operand.as(:base) >> sup_paren.as(:sup)).as(:mini_sup) }
40
+ rule(:mini_sub_value) do
41
+ (sub_sup_operand.as(:base) >> sub_paren.as(:sub)).as(:mini_sub)
42
+ end
43
+ rule(:mini_sup_value) do
44
+ (sub_sup_operand.as(:base) >> sup_paren.as(:sup)).as(:mini_sup)
45
+ end
32
46
 
33
- rule(:pre_script_base) { (operand.as(:base) >> (subsup | mini_subsup | subscript_value | supscript_value).maybe) }
47
+ rule(:pre_script_base) do
48
+ operand.as(:base) >> (subsup | mini_subsup | subscript_value | supscript_value).maybe
49
+ end
34
50
 
35
51
  rule(:sub_sup_override) { sub_override | sup_override }
36
- rule(:operator_symbols) { combined_symbols | negatable_symbols | operator }
37
- rule(:invisible_space?) { (invisible_unicode? >> invisible_times.maybe).maybe }
38
- rule(:prescript_values) { operand | mini_sub_sup | operator_symbols | binary_symbols }
52
+ rule(:operator_symbols) do
53
+ combined_symbols | negatable_symbols | operator
54
+ end
55
+ rule(:invisible_space?) do
56
+ (invisible_unicode? >> invisible_times.maybe).maybe
57
+ end
58
+ rule(:prescript_values) do
59
+ operand | mini_sub_sup | operator_symbols | binary_symbols
60
+ end
39
61
 
40
- rule(:power_base_script) { (base_value >> subsup).as(:subsup_exp) | subscript.as(:sub_exp) | supscript.as(:sup_exp) }
62
+ rule(:power_base_script) do
63
+ (base_value >> subsup).as(:subsup_exp) | subscript.as(:sub_exp) | supscript.as(:sup_exp)
64
+ end
41
65
 
42
- rule(:mini_sub_sup_present?) { mini_sub_value.present? | mini_sup_value.present? | mini_subsup.present? }
66
+ rule(:mini_sub_sup_present?) do
67
+ mini_sub_value.present? | mini_sup_value.present? | mini_subsup.present?
68
+ end
43
69
 
44
70
  rule(:subscript_value) do
45
71
  (sub_paren | baseless_sub.as(:sub)) >> recursive_baseless_sub_exp.maybe
@@ -50,8 +76,8 @@ module Plurimath
50
76
  end
51
77
 
52
78
  rule(:pre_sub_sup_override) do
53
- base_syntax >> op_size_overrides_symbols >> prescript_values.as(:pre_subscript) |
54
- power_syntax >> op_size_overrides_symbols >> prescript_values.as(:pre_supscript)
79
+ (base_syntax >> op_size_overrides_symbols >> prescript_values.as(:pre_subscript)) |
80
+ (power_syntax >> op_size_overrides_symbols >> prescript_values.as(:pre_supscript))
55
81
  end
56
82
 
57
83
  rule(:naryand_recursion) do
@@ -84,11 +110,11 @@ module Plurimath
84
110
  end
85
111
 
86
112
  rule(:naryand_values) do
87
- binomial_fraction.absent? >> fraction.as(:frac) |
113
+ (binomial_fraction.absent? >> fraction.as(:frac)) |
88
114
  (exp_bracket >> (subsup | subscript_value | supscript_value).maybe) |
89
115
  (exp_script >> space?) |
90
- binomial_fraction.as(:frac) >> space? |
91
- negatable_symbols.absent? >> sub_sup_operand
116
+ (binomial_fraction.as(:frac) >> space?) |
117
+ (negatable_symbols.absent? >> sub_sup_operand)
92
118
  end
93
119
 
94
120
  rule(:mini_sub_sup) do
@@ -110,27 +136,27 @@ module Plurimath
110
136
  end
111
137
 
112
138
  rule(:base_value) do
113
- op_nary.present? >> op_nary >> invisible_space? >> number.as(:mask).maybe |
114
- script_base.as(:base) >> invisible_space?
139
+ (op_nary.present? >> op_nary >> invisible_space? >> number.as(:mask).maybe) |
140
+ (script_base.as(:base) >> invisible_space?)
115
141
  end
116
142
 
117
143
  rule(:subsup) do
118
- op_size_overrides_symbols.absent? >> baseless_sub.as(:sub) >> (sup_override.as(:sup) | baseless_sup.as(:sup)) |
119
- op_size_overrides_symbols.absent? >> baseless_sup.as(:sup) >> (sub_override.as(:sub) | baseless_sub.as(:sub)) |
120
- (sub_override.as(:sub) | baseless_sub.as(:sub)) >> baseless_sup.as(:sup) |
121
- (sup_override.as(:sup) | baseless_sup.as(:sup)) >> baseless_sub.as(:sub)
144
+ (op_size_overrides_symbols.absent? >> baseless_sub.as(:sub) >> (sup_override.as(:sup) | baseless_sup.as(:sup))) |
145
+ (op_size_overrides_symbols.absent? >> baseless_sup.as(:sup) >> (sub_override.as(:sub) | baseless_sub.as(:sub))) |
146
+ ((sub_override.as(:sub) | baseless_sub.as(:sub)) >> baseless_sup.as(:sup)) |
147
+ ((sup_override.as(:sup) | baseless_sup.as(:sup)) >> baseless_sub.as(:sub))
122
148
  end
123
149
 
124
150
  rule(:mini_subsup) do
125
- sub_paren.as(:sub) >> sup_paren.as(:sup) |
126
- sup_paren.as(:sup) >> sub_paren.as(:sub)
151
+ (sub_paren.as(:sub) >> sup_paren.as(:sup)) |
152
+ (sup_paren.as(:sup) >> sub_paren.as(:sub))
127
153
  end
128
154
 
129
155
  rule(:accents_subsup) do
130
- baseless_sub.as(:sub) >> baseless_sup.as(:sup) |
131
- baseless_sup.as(:sup) >> baseless_sub.as(:sub) |
132
- sub_paren.as(:sub) >> sup_paren.as(:sup) |
133
- sup_paren.as(:sup) >> sub_paren.as(:sub) |
156
+ (baseless_sub.as(:sub) >> baseless_sup.as(:sup)) |
157
+ (baseless_sup.as(:sup) >> baseless_sub.as(:sub)) |
158
+ (sub_paren.as(:sub) >> sup_paren.as(:sup)) |
159
+ (sup_paren.as(:sup) >> sub_paren.as(:sub)) |
134
160
  baseless_sub.as(:sub) |
135
161
  baseless_sup.as(:sup) |
136
162
  sub_paren.as(:sub) |
@@ -138,38 +164,38 @@ module Plurimath
138
164
  end
139
165
 
140
166
  rule(:mini_power_base) do
141
- sup_paren.as(:pre_supscript) >> sub_paren.as(:pre_subscript).maybe >> mini_values.as(:mini_base) >> sub_paren.as(:mini_sub).maybe >> mini_values.as(:mini_sup) |
142
- sub_paren.as(:pre_subscript) >> sup_paren.as(:pre_supscript).maybe >> mini_values.as(:mini_base) >> sup_paren.as(:mini_sup).maybe >> mini_values.as(:mini_sub) |
143
- mini_values.as(:mini_base) >> sub_paren.as(:mini_sub) >> mini_values.as(:mini_sup) |
144
- mini_values.as(:mini_base) >> sup_paren.as(:mini_sup) >> sub_paren.as(:mini_sub) |
145
- mini_values.as(:mini_base) >> mini_values.as(:mini_sup) |
146
- mini_values.as(:mini_base) >> sub_paren.as(:mini_sub)
167
+ (sup_paren.as(:pre_supscript) >> sub_paren.as(:pre_subscript).maybe >> mini_values.as(:mini_base) >> sub_paren.as(:mini_sub).maybe >> mini_values.as(:mini_sup)) |
168
+ (sub_paren.as(:pre_subscript) >> sup_paren.as(:pre_supscript).maybe >> mini_values.as(:mini_base) >> sup_paren.as(:mini_sup).maybe >> mini_values.as(:mini_sub)) |
169
+ (mini_values.as(:mini_base) >> sub_paren.as(:mini_sub) >> mini_values.as(:mini_sup)) |
170
+ (mini_values.as(:mini_base) >> sup_paren.as(:mini_sup) >> sub_paren.as(:mini_sub)) |
171
+ (mini_values.as(:mini_base) >> mini_values.as(:mini_sup)) |
172
+ (mini_values.as(:mini_base) >> sub_paren.as(:mini_sub))
147
173
  end
148
174
 
149
175
  rule(:mini_values) do
150
176
  op_sup_operators |
151
- op_sub_operators |
152
- op_sup_digits |
153
- op_sub_digits |
154
- op_sup_alpha |
155
- op_sub_alpha
177
+ op_sub_operators |
178
+ op_sup_digits |
179
+ op_sub_digits |
180
+ op_sup_alpha |
181
+ op_sub_alpha
156
182
  end
157
183
 
158
184
  rule(:exp_script) do
159
- op_nary.present? >> nary_sub_sup.as(:nary) |
160
- op_unary_functions.present? >> unary_sub_sup.as(:unary_subsup) |
161
- accents.present? >> (accents.as(:base) >> accents_subsup).as(:accents_subsup) |
185
+ (op_nary.present? >> nary_sub_sup.as(:nary)) |
186
+ (op_unary_functions.present? >> unary_sub_sup.as(:unary_subsup)) |
187
+ (accents.present? >> (accents.as(:base) >> accents_subsup).as(:accents_subsup)) |
162
188
  power_base_script |
163
189
  (base_value >> sub_sup_override).as(:override_subsup) |
164
- pre_sub_sup_override.as(:pre_override_subsup) >> pre_script_base |
190
+ (pre_sub_sup_override.as(:pre_override_subsup) >> pre_script_base) |
165
191
  (paren_wrap_rule(pre_subsup) >> space? >> pre_script_base).as(:pre_script) |
166
192
  mini_sub_sup |
167
193
  mini_power_base
168
194
  end
169
195
 
170
196
  rule(:pre_subsup) do
171
- pre_subscript >> pre_supscript |
172
- pre_supscript >> pre_subscript |
197
+ (pre_subscript >> pre_supscript) |
198
+ (pre_supscript >> pre_subscript) |
173
199
  pre_subscript |
174
200
  pre_supscript
175
201
  end
@@ -177,7 +203,7 @@ module Plurimath
177
203
  rule(:sub_sup_operand) do
178
204
  binary_symbols |
179
205
  accents |
180
- op_unary_functions >> invisible_unicode? |
206
+ (op_unary_functions >> invisible_unicode?) |
181
207
  alpha_numeric_values |
182
208
  number |
183
209
  an_math |
@@ -191,37 +217,37 @@ module Plurimath
191
217
  end
192
218
 
193
219
  rule(:sub_alpha_digits) do
194
- (op_sub_digits >> op_sub_alpha).as(:expr) >> sub_paren.as(:sub_recursion).maybe |
195
- (op_sub_alpha >> op_sub_digits).as(:expr) >> sub_paren.as(:sub_recursion).maybe |
196
- op_sub_alpha >> sub_paren.as(:sub_recursion_expr).maybe |
197
- op_sub_digits >> sub_paren.as(:sub_recursion_expr).maybe |
198
- op_sub_operators >> sub_paren.as(:sub_recursions).maybe
220
+ ((op_sub_digits >> op_sub_alpha).as(:expr) >> sub_paren.as(:sub_recursion).maybe) |
221
+ ((op_sub_alpha >> op_sub_digits).as(:expr) >> sub_paren.as(:sub_recursion).maybe) |
222
+ (op_sub_alpha >> sub_paren.as(:sub_recursion_expr).maybe) |
223
+ (op_sub_digits >> sub_paren.as(:sub_recursion_expr).maybe) |
224
+ (op_sub_operators >> sub_paren.as(:sub_recursions).maybe)
199
225
  end
200
226
 
201
227
  rule(:sup_alpha_digits) do
202
- (op_sup_digits >> op_sup_alpha).as(:expr) >> sup_paren.as(:sup_recursion).maybe |
203
- (op_sup_alpha >> op_sup_digits).as(:expr) >> sup_paren.as(:sup_recursion).maybe |
204
- op_sup_alpha >> sup_paren.as(:sup_recursion_expr).maybe |
205
- op_sup_digits >> sup_paren.as(:sup_recursion_expr).maybe |
206
- op_sup_operators >> sup_paren.as(:sup_recursions).maybe
228
+ ((op_sup_digits >> op_sup_alpha).as(:expr) >> sup_paren.as(:sup_recursion).maybe) |
229
+ ((op_sup_alpha >> op_sup_digits).as(:expr) >> sup_paren.as(:sup_recursion).maybe) |
230
+ (op_sup_alpha >> sup_paren.as(:sup_recursion_expr).maybe) |
231
+ (op_sup_digits >> sup_paren.as(:sup_recursion_expr).maybe) |
232
+ (op_sup_operators >> sup_paren.as(:sup_recursions).maybe)
207
233
  end
208
234
 
209
235
  rule(:sub_paren) do
210
- (op_sub_open_paren >> sub_alpha_digits.as(:mini_expr) >> op_sub_close_paren).as(:mini_intermediate_exp) >> sub_paren.maybe |
211
- sub_alpha_digits >> sub_paren.maybe
236
+ ((op_sub_open_paren >> sub_alpha_digits.as(:mini_expr) >> op_sub_close_paren).as(:mini_intermediate_exp) >> sub_paren.maybe) |
237
+ (sub_alpha_digits >> sub_paren.maybe)
212
238
  end
213
239
 
214
240
  rule(:sup_paren) do
215
- (op_sup_open_paren >> sup_alpha_digits.as(:mini_expr) >> op_sup_close_paren).as(:mini_intermediate_exp) >> sup_paren.maybe |
216
- sup_alpha_digits >> sup_paren.maybe
241
+ ((op_sup_open_paren >> sup_alpha_digits.as(:mini_expr) >> op_sup_close_paren).as(:mini_intermediate_exp) >> sup_paren.maybe) |
242
+ (sup_alpha_digits >> sup_paren.maybe)
217
243
  end
218
244
 
219
245
  rule(:sub_sup_values) do
220
246
  (operator_symbols.as(:expr) >> (((mini_sub_sup | sub_or_sup) >> space?) >> bracketed_soperand.maybe)) |
221
247
  (operator_symbols.as(:expr) >> bracketed_soperand) |
222
248
  (((primes | prefixed_primes).as(:symbol).as(:first_value) >> repeated_accent_symbols).as(:accents) >> (sub_or_sup.maybe >> space? >> bracketed_soperand).maybe) |
223
- bracketed_soperand >> str("−").absent? >> operator_symbols.absent? >> sub_sup_values.as(:expr).maybe |
224
- sub_sup_binary_absent >> str("−").absent? >> operator_symbols.absent? >> sub_sup_values.as(:expr).maybe |
249
+ (bracketed_soperand >> str("−").absent? >> operator_symbols.absent? >> sub_sup_values.as(:expr).maybe) |
250
+ (sub_sup_binary_absent >> str("−").absent? >> operator_symbols.absent? >> sub_sup_values.as(:expr).maybe) |
225
251
  bracketed_soperand |
226
252
  prefixed_primes |
227
253
  primes |
@@ -229,10 +255,10 @@ module Plurimath
229
255
  end
230
256
 
231
257
  rule(:alpha_numeric_values) do
232
- alpha_ascii >> alpha_numeric_values.as(:expr) |
233
- (number | n_ascii) >> alpha_numeric_values.as(:expr) |
234
- alpha_ascii |
235
- (number | n_ascii)
258
+ (alpha_ascii >> alpha_numeric_values.as(:expr)) |
259
+ ((number | n_ascii) >> alpha_numeric_values.as(:expr)) |
260
+ alpha_ascii |
261
+ (number | n_ascii)
236
262
  end
237
263
 
238
264
  def paren_wrap_rule(passed_rule)
@@ -241,13 +267,13 @@ module Plurimath
241
267
  end
242
268
 
243
269
  def baseless_sub_values(soperand_name)
244
- (mini_sub_sup | sub_sup_paren).as(soperand_name) >> recursive_baseless_sub_exp.maybe >> sub_sup_values.maybe |
245
- sub_sup_values.as(soperand_name) >> recursive_baseless_sub_exp.maybe
270
+ ((mini_sub_sup | sub_sup_paren).as(soperand_name) >> recursive_baseless_sub_exp.maybe >> sub_sup_values.maybe) |
271
+ (sub_sup_values.as(soperand_name) >> recursive_baseless_sub_exp.maybe)
246
272
  end
247
273
 
248
274
  def baseless_sup_values(soperand_name)
249
- (mini_sub_sup | sub_sup_paren).as(soperand_name) >> recursive_baseless_sup_exp.maybe >> sub_sup_values.maybe |
250
- sub_sup_values.as(soperand_name) >> recursive_baseless_sup_exp.maybe
275
+ ((mini_sub_sup | sub_sup_paren).as(soperand_name) >> recursive_baseless_sup_exp.maybe >> sub_sup_values.maybe) |
276
+ (sub_sup_values.as(soperand_name) >> recursive_baseless_sup_exp.maybe)
251
277
  end
252
278
  end
253
279
  end
@@ -3,6 +3,7 @@
3
3
  module Plurimath
4
4
  class UnicodeMath
5
5
  class Transform < Parslet::Transform
6
+ include Plurimath::BaseNumberPrefix::Transform
6
7
 
7
8
  rule(td: simple(:td)) { Math::Function::Td.new([td]) }
8
9
  rule(tr: simple(:tr)) { Math::Function::Tr.new([tr]) }
@@ -437,7 +437,7 @@ lang: nil)
437
437
  symbol = Mathml::Constants::UNICODE_SYMBOLS[unicode.strip.to_sym]
438
438
  if classes.include?(symbol&.strip)
439
439
  get_class(symbol.strip).new
440
- elsif classes.any?(string&.strip)
440
+ elsif classes.any?(string&.strip) && !(lang == :mathml && Mathml::Constants.accent_word?(string))
441
441
  get_class(string.strip).new
442
442
  elsif omml
443
443
  text_classes(string,
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Plurimath
4
- VERSION = "0.11.0"
4
+ VERSION = "0.11.3"
5
5
  end
data/lib/plurimath.rb CHANGED
@@ -7,12 +7,14 @@ require "plurimath/xml_engine"
7
7
 
8
8
  module Plurimath
9
9
  autoload :Asciimath, "plurimath/asciimath"
10
+ autoload :BaseNumberPrefix, "plurimath/base_number_prefix"
10
11
  autoload :Cli, "plurimath/cli" unless RUBY_ENGINE == "opal"
11
12
  autoload :Configuration, "plurimath/configuration"
12
13
  autoload :Deprecation, "plurimath/deprecation"
13
14
  autoload :Error, "plurimath/errors/error"
14
15
  autoload :ConfigurationError, "plurimath/errors/configuration_error"
15
16
  autoload :DeprecationError, "plurimath/errors/deprecation_error"
17
+ autoload :Errors, "plurimath/errors"
16
18
  autoload :Formatter, "plurimath/formatter"
17
19
  autoload :Html, "plurimath/html"
18
20
  autoload :Latex, "plurimath/latex"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: plurimath
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.11.0
4
+ version: 0.11.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-06-18 00:00:00.000000000 Z
11
+ date: 2026-06-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bigdecimal
@@ -192,6 +192,7 @@ files:
192
192
  - lib/plurimath/asciimath/parse.rb
193
193
  - lib/plurimath/asciimath/parser.rb
194
194
  - lib/plurimath/asciimath/transform.rb
195
+ - lib/plurimath/base_number_prefix.rb
195
196
  - lib/plurimath/cli.rb
196
197
  - lib/plurimath/configuration.rb
197
198
  - lib/plurimath/deprecation.rb
@@ -199,29 +200,43 @@ files:
199
200
  - lib/plurimath/errors/configuration_error.rb
200
201
  - lib/plurimath/errors/deprecation_error.rb
201
202
  - lib/plurimath/errors/error.rb
202
- - lib/plurimath/errors/formatter/unsupported_base.rb
203
- - lib/plurimath/errors/formatter/unsupported_locale.rb
203
+ - lib/plurimath/errors/evaluation.rb
204
+ - lib/plurimath/errors/evaluation/division_by_zero_error.rb
205
+ - lib/plurimath/errors/evaluation/error.rb
206
+ - lib/plurimath/errors/evaluation/invalid_binding_error.rb
207
+ - lib/plurimath/errors/evaluation/invalid_binding_key_error.rb
208
+ - lib/plurimath/errors/evaluation/math_domain_error.rb
209
+ - lib/plurimath/errors/evaluation/missing_variable_error.rb
210
+ - lib/plurimath/errors/evaluation/non_finite_result_error.rb
211
+ - lib/plurimath/errors/evaluation/unsupported_expression_error.rb
212
+ - lib/plurimath/errors/invalid_number.rb
204
213
  - lib/plurimath/errors/invalid_type_error.rb
205
214
  - lib/plurimath/errors/omml/unsupported_node_error.rb
206
215
  - lib/plurimath/errors/parse_error.rb
207
216
  - lib/plurimath/errors/parse_option_error.rb
217
+ - lib/plurimath/errors/unsupported_base.rb
218
+ - lib/plurimath/errors/unsupported_locale.rb
208
219
  - lib/plurimath/formatter.rb
209
220
  - lib/plurimath/formatter/numbers.rb
210
221
  - lib/plurimath/formatter/numbers/base.rb
211
222
  - lib/plurimath/formatter/numbers/base_notation.rb
212
223
  - lib/plurimath/formatter/numbers/digit_sequence.rb
213
224
  - lib/plurimath/formatter/numbers/format_options.rb
225
+ - lib/plurimath/formatter/numbers/formatted_notation.rb
226
+ - lib/plurimath/formatter/numbers/formatted_number.rb
214
227
  - lib/plurimath/formatter/numbers/fraction.rb
215
228
  - lib/plurimath/formatter/numbers/integer.rb
229
+ - lib/plurimath/formatter/numbers/mathml_renderer.rb
216
230
  - lib/plurimath/formatter/numbers/notation_renderer.rb
217
231
  - lib/plurimath/formatter/numbers/number_renderer.rb
232
+ - lib/plurimath/formatter/numbers/omml_renderer.rb
218
233
  - lib/plurimath/formatter/numbers/parts.rb
219
- - lib/plurimath/formatter/numbers/parts_renderer.rb
220
234
  - lib/plurimath/formatter/numbers/precision_resolver.rb
221
235
  - lib/plurimath/formatter/numbers/sign_renderer.rb
222
236
  - lib/plurimath/formatter/numbers/significant.rb
223
237
  - lib/plurimath/formatter/numbers/source.rb
224
238
  - lib/plurimath/formatter/numbers/symbol_resolver.rb
239
+ - lib/plurimath/formatter/numbers/text_renderer.rb
225
240
  - lib/plurimath/formatter/standard.rb
226
241
  - lib/plurimath/formatter/supported_locales.rb
227
242
  - lib/plurimath/html.rb
@@ -237,6 +252,10 @@ files:
237
252
  - lib/plurimath/latex/transform.rb
238
253
  - lib/plurimath/math.rb
239
254
  - lib/plurimath/math/core.rb
255
+ - lib/plurimath/math/evaluation.rb
256
+ - lib/plurimath/math/evaluation/evaluator.rb
257
+ - lib/plurimath/math/evaluation/expression_parser.rb
258
+ - lib/plurimath/math/evaluation/iteration.rb
240
259
  - lib/plurimath/math/formula.rb
241
260
  - lib/plurimath/math/formula/mrow.rb
242
261
  - lib/plurimath/math/formula/mstyle.rb
@@ -1,21 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Plurimath
4
- module Formatter
5
- class UnsupportedBase < Plurimath::Error
6
- def initialize(base, supported_bases)
7
- @base = base
8
- @supported = supported_bases.keys.map do |key|
9
- key.to_s.inspect
10
- end.join(", ")
11
- end
12
-
13
- def to_s
14
- <<~MESSAGE
15
- [plurimath] Unsupported base `#{@base}` for number formatting.
16
- [plurimath] The formatter `:base` option must be one of: #{@supported}.
17
- MESSAGE
18
- end
19
- end
20
- end
21
- end
@@ -1,30 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Plurimath
4
- module Formatter
5
- module Numbers
6
- # Renders already-transformed Parts into localized integer/fraction text.
7
- class PartsRenderer
8
- def initialize(integer_formatter:, fraction_formatter:)
9
- @integer_formatter = integer_formatter
10
- @fraction_formatter = fraction_formatter
11
- end
12
-
13
- def render(parts)
14
- rendered = integer_formatter.format_groups(parts.integer_digits)
15
- return rendered unless parts.fractional?
16
-
17
- "#{rendered}#{fraction_formatter.decimal}#{formatted_fraction(parts)}"
18
- end
19
-
20
- private
21
-
22
- attr_reader :fraction_formatter, :integer_formatter
23
-
24
- def formatted_fraction(parts)
25
- fraction_formatter.format_groups(parts.fraction_digits)
26
- end
27
- end
28
- end
29
- end
30
- end