plurimath 0.1.0 → 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (142) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test.yml +33 -0
  3. data/.gitignore +1 -0
  4. data/.rubocop.yml +2 -0
  5. data/AsciiMath-Supported-Data.adoc +280 -0
  6. data/Gemfile +1 -0
  7. data/Latex-Supported-Data.adoc +1872 -0
  8. data/MathML-Supported-Data.adoc +270 -0
  9. data/README.adoc +94 -0
  10. data/lib/plurimath/asciimath/constants.rb +301 -0
  11. data/lib/plurimath/asciimath/parse.rb +121 -0
  12. data/lib/plurimath/asciimath/parser.rb +25 -0
  13. data/lib/plurimath/asciimath/transform.rb +395 -0
  14. data/lib/plurimath/asciimath.rb +16 -0
  15. data/lib/plurimath/html/constants.rb +50 -0
  16. data/lib/plurimath/html/parse.rb +149 -0
  17. data/lib/plurimath/html/parser.rb +26 -0
  18. data/lib/plurimath/html/transform.rb +363 -0
  19. data/lib/plurimath/html.rb +15 -0
  20. data/lib/plurimath/latex/constants.rb +1990 -0
  21. data/lib/plurimath/latex/parse.rb +198 -0
  22. data/lib/plurimath/latex/parser.rb +25 -0
  23. data/lib/plurimath/latex/transform.rb +458 -0
  24. data/lib/plurimath/latex.rb +15 -0
  25. data/lib/plurimath/math/formula.rb +51 -0
  26. data/lib/plurimath/math/function/abs.rb +12 -0
  27. data/lib/plurimath/math/function/arccos.rb +12 -0
  28. data/lib/plurimath/math/function/arcsin.rb +12 -0
  29. data/lib/plurimath/math/function/arctan.rb +12 -0
  30. data/lib/plurimath/math/function/bar.rb +16 -0
  31. data/lib/plurimath/math/function/base.rb +36 -0
  32. data/lib/plurimath/math/function/binary_function.rb +58 -0
  33. data/lib/plurimath/math/function/cancel.rb +12 -0
  34. data/lib/plurimath/math/function/ceil.rb +12 -0
  35. data/lib/plurimath/math/function/color.rb +23 -0
  36. data/lib/plurimath/math/function/cos.rb +12 -0
  37. data/lib/plurimath/math/function/cosh.rb +12 -0
  38. data/lib/plurimath/math/function/cot.rb +12 -0
  39. data/lib/plurimath/math/function/coth.rb +12 -0
  40. data/lib/plurimath/math/function/csc.rb +12 -0
  41. data/lib/plurimath/math/function/csch.rb +12 -0
  42. data/lib/plurimath/math/function/ddot.rb +12 -0
  43. data/lib/plurimath/math/function/deg.rb +12 -0
  44. data/lib/plurimath/math/function/det.rb +12 -0
  45. data/lib/plurimath/math/function/dim.rb +12 -0
  46. data/lib/plurimath/math/function/dot.rb +12 -0
  47. data/lib/plurimath/math/function/exp.rb +12 -0
  48. data/lib/plurimath/math/function/f.rb +12 -0
  49. data/lib/plurimath/math/function/fenced.rb +27 -0
  50. data/lib/plurimath/math/function/floor.rb +12 -0
  51. data/lib/plurimath/math/function/font_style/bold.rb +18 -0
  52. data/lib/plurimath/math/function/font_style/double_struck.rb +18 -0
  53. data/lib/plurimath/math/function/font_style/fraktur.rb +18 -0
  54. data/lib/plurimath/math/function/font_style/monospace.rb +18 -0
  55. data/lib/plurimath/math/function/font_style/sans-serif.rb +18 -0
  56. data/lib/plurimath/math/function/font_style/script.rb +18 -0
  57. data/lib/plurimath/math/function/font_style.rb +25 -0
  58. data/lib/plurimath/math/function/frac.rb +23 -0
  59. data/lib/plurimath/math/function/g.rb +12 -0
  60. data/lib/plurimath/math/function/gcd.rb +12 -0
  61. data/lib/plurimath/math/function/glb.rb +12 -0
  62. data/lib/plurimath/math/function/hat.rb +12 -0
  63. data/lib/plurimath/math/function/hom.rb +12 -0
  64. data/lib/plurimath/math/function/inf.rb +17 -0
  65. data/lib/plurimath/math/function/int.rb +17 -0
  66. data/lib/plurimath/math/function/ker.rb +12 -0
  67. data/lib/plurimath/math/function/lcm.rb +12 -0
  68. data/lib/plurimath/math/function/left.rb +20 -0
  69. data/lib/plurimath/math/function/lg.rb +12 -0
  70. data/lib/plurimath/math/function/lim.rb +23 -0
  71. data/lib/plurimath/math/function/liminf.rb +12 -0
  72. data/lib/plurimath/math/function/limits.rb +18 -0
  73. data/lib/plurimath/math/function/limsup.rb +12 -0
  74. data/lib/plurimath/math/function/ln.rb +12 -0
  75. data/lib/plurimath/math/function/log.rb +29 -0
  76. data/lib/plurimath/math/function/lub.rb +12 -0
  77. data/lib/plurimath/math/function/max.rb +12 -0
  78. data/lib/plurimath/math/function/min.rb +12 -0
  79. data/lib/plurimath/math/function/mod.rb +29 -0
  80. data/lib/plurimath/math/function/multiscript.rb +11 -0
  81. data/lib/plurimath/math/function/norm.rb +16 -0
  82. data/lib/plurimath/math/function/obrace.rb +12 -0
  83. data/lib/plurimath/math/function/oint.rb +17 -0
  84. data/lib/plurimath/math/function/over.rb +29 -0
  85. data/lib/plurimath/math/function/overset.rb +23 -0
  86. data/lib/plurimath/math/function/power.rb +36 -0
  87. data/lib/plurimath/math/function/power_base.rb +33 -0
  88. data/lib/plurimath/math/function/prod.rb +29 -0
  89. data/lib/plurimath/math/function/right.rb +24 -0
  90. data/lib/plurimath/math/function/root.rb +23 -0
  91. data/lib/plurimath/math/function/sec.rb +12 -0
  92. data/lib/plurimath/math/function/sech.rb +12 -0
  93. data/lib/plurimath/math/function/sin.rb +12 -0
  94. data/lib/plurimath/math/function/sinh.rb +12 -0
  95. data/lib/plurimath/math/function/sqrt.rb +16 -0
  96. data/lib/plurimath/math/function/stackrel.rb +12 -0
  97. data/lib/plurimath/math/function/substack.rb +17 -0
  98. data/lib/plurimath/math/function/sum.rb +29 -0
  99. data/lib/plurimath/math/function/sup.rb +12 -0
  100. data/lib/plurimath/math/function/table/align.rb +24 -0
  101. data/lib/plurimath/math/function/table/array.rb +25 -0
  102. data/lib/plurimath/math/function/table/bmatrix.rb +26 -0
  103. data/lib/plurimath/math/function/table/matrix.rb +24 -0
  104. data/lib/plurimath/math/function/table/multline.rb +24 -0
  105. data/lib/plurimath/math/function/table/pmatrix.rb +24 -0
  106. data/lib/plurimath/math/function/table/split.rb +24 -0
  107. data/lib/plurimath/math/function/table/vmatrix.rb +25 -0
  108. data/lib/plurimath/math/function/table.rb +54 -0
  109. data/lib/plurimath/math/function/tan.rb +12 -0
  110. data/lib/plurimath/math/function/tanh.rb +12 -0
  111. data/lib/plurimath/math/function/td.rb +32 -0
  112. data/lib/plurimath/math/function/ternary_function.rb +52 -0
  113. data/lib/plurimath/math/function/text.rb +44 -0
  114. data/lib/plurimath/math/function/tilde.rb +12 -0
  115. data/lib/plurimath/math/function/tr.rb +30 -0
  116. data/lib/plurimath/math/function/ubrace.rb +12 -0
  117. data/lib/plurimath/math/function/ul.rb +12 -0
  118. data/lib/plurimath/math/function/unary_function.rb +46 -0
  119. data/lib/plurimath/math/function/underover.rb +12 -0
  120. data/lib/plurimath/math/function/underset.rb +12 -0
  121. data/lib/plurimath/math/function/vec.rb +16 -0
  122. data/lib/plurimath/math/function.rb +14 -0
  123. data/lib/plurimath/math/number.rb +37 -0
  124. data/lib/plurimath/math/symbol.rb +43 -0
  125. data/lib/plurimath/math.rb +56 -0
  126. data/lib/plurimath/mathml/constants.rb +295 -0
  127. data/lib/plurimath/mathml/parse.rb +68 -0
  128. data/lib/plurimath/mathml/parser.rb +26 -0
  129. data/lib/plurimath/mathml/transform.rb +200 -0
  130. data/lib/plurimath/mathml.rb +16 -0
  131. data/lib/plurimath/omml/constants.rb +154 -0
  132. data/lib/plurimath/omml/parser.rb +22 -0
  133. data/lib/plurimath/omml/transform.rb +216 -0
  134. data/lib/plurimath/omml.rb +15 -0
  135. data/lib/plurimath/unicode.rb +15 -0
  136. data/lib/plurimath/unitsml.rb +15 -0
  137. data/lib/plurimath/utility.rb +73 -0
  138. data/lib/plurimath/version.rb +3 -1
  139. data/lib/plurimath.rb +3 -5
  140. data/plurimath.gemspec +4 -3
  141. metadata +169 -9
  142. data/README.md +0 -40
@@ -0,0 +1,198 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "parslet"
4
+ module Plurimath
5
+ class Latex
6
+ class Parse < Parslet::Parser
7
+ rule(:base) { str("_") }
8
+ rule(:power) { str("^") }
9
+ rule(:slash) { str("\\") }
10
+ rule(:unary) { slash >> unary_classes }
11
+ rule(:ending) { (slash >> str("end") >> intermediate_exp).as(:ending) }
12
+ rule(:binary) { slash >> binary_classes }
13
+
14
+ rule(:array_args) { (str("{") >> expression >> str("}")).as(:args) }
15
+ rule(:under_over) { slash >> underover_classes }
16
+
17
+ rule(:begining) do
18
+ (slash >> str("begin") >> intermediate_exp).as(:begining)
19
+ end
20
+
21
+ rule(:symbols) do
22
+ arr_to_expression(Constants::SYMBOLS.keys, :symbols)
23
+ end
24
+
25
+ rule(:operators) do
26
+ arr_to_expression(Constants::OPERATORS, :operant)
27
+ end
28
+
29
+ rule(:numeric_values) do
30
+ arr_to_expression(Constants::NUMERIC_VALUES, :numeric_values)
31
+ end
32
+
33
+ rule(:unary_classes) do
34
+ arr_to_expression(Constants::UNARY_CLASSES, :unary)
35
+ end
36
+
37
+ rule(:binary_classes) do
38
+ arr_to_expression(Constants::BINARY_CLASSES, :binary)
39
+ end
40
+
41
+ rule(:underover_classes) do
42
+ arr_to_expression(Constants::UNDEROVER_CLASSES, :binary)
43
+ end
44
+
45
+ rule(:power_base_classes) do
46
+ arr_to_expression(Constants::POWER_BASE_CLASSES, :binary)
47
+ end
48
+
49
+ rule(:math_operators_classes) do
50
+ arr_to_expression(Constants::MATH_OPERATORS, :unary_functions)
51
+ end
52
+
53
+ rule(:lparen) do
54
+ arr_to_expression(Constants::PARENTHESIS.keys, :lparen)
55
+ end
56
+
57
+ rule(:rparen) do
58
+ arr_to_expression(Constants::PARENTHESIS.values, :rparen)
59
+ end
60
+
61
+ rule(:subscript) do
62
+ intermediate_exp >> base >> intermediate_exp.as(:subscript)
63
+ end
64
+
65
+ rule(:supscript) do
66
+ intermediate_exp >> power >> intermediate_exp.as(:supscript)
67
+ end
68
+
69
+ rule(:environment) do
70
+ arr_to_expression(Constants::MATRICES.keys, :environment)
71
+ end
72
+
73
+ rule(:fonts) do
74
+ arr_to_expression(Constants::FONT_STYLES, :fonts)
75
+ end
76
+
77
+ rule(:math_operators) do
78
+ slash >> math_operators_classes >> str("\\limits")
79
+ end
80
+
81
+ rule(:left_right) do
82
+ (str("\\left").as(:left) >> lparen >> expression.as(:expression) >> str("\\right").as(:right) >> rparen)
83
+ end
84
+
85
+ rule(:sqrt_arg) do
86
+ str("[").as(:lparen) >> (expression | str("")) >> str("]").as(:rparen)
87
+ end
88
+
89
+ rule(:limits) do
90
+ (math_operators >> base >> intermediate_exp.as(:base) >> power >> intermediate_exp.as(:power)) |
91
+ (math_operators >> power >> intermediate_exp.as(:power) >> base >> intermediate_exp.as(:base))
92
+ end
93
+
94
+ rule(:symbol_class_commands) do
95
+ (slash >> symbols) |
96
+ (unary >> intermediate_exp.as(:first_value)).as(:unary_functions) |
97
+ unary.as(:unary_functions) |
98
+ binary |
99
+ under_over |
100
+ environment |
101
+ operators |
102
+ numeric_values |
103
+ (slash >> power_base_classes) |
104
+ (slash >> fonts >> (binary_functions | intermediate_exp).as(:intermediate_exp))
105
+ end
106
+
107
+ rule(:symbol_text_or_integer) do
108
+ symbol_class_commands |
109
+ match["a-zA-Z"].repeat(1).as(:text) |
110
+ (str('"') >> match("[^\"]").repeat >> str('"')).as(:text) |
111
+ match(/\d+(\.[0-9]+)|\d/).repeat(1).as(:number) |
112
+ str("\\\\").as("\\\\")
113
+ end
114
+
115
+ rule(:intermediate_exp) do
116
+ (lparen >> expression.as(:expression) >> rparen) |
117
+ (lparen >> str("") >> rparen) |
118
+ symbol_text_or_integer
119
+ end
120
+
121
+ rule(:power_base) do
122
+ (subscript >> power >> intermediate_exp.as(:supscript)).as(:power_base) |
123
+ (supscript >> base >> intermediate_exp.as(:subscript)).as(:power_base) |
124
+ supscript.as(:power) |
125
+ subscript.as(:base)
126
+ end
127
+
128
+ rule(:binary_functions) do
129
+ (slash >> str("sqrt").as(:root) >> sqrt_arg.as(:first_value) >> intermediate_exp.as(:second_value)).as(:binary) |
130
+ (slash >> str("sqrt").as(:sqrt) >> intermediate_exp.as(:intermediate_exp)).as(:binary) |
131
+ (intermediate_exp.as(:first_value) >> under_over >> intermediate_exp.as(:second_value)).as(:under_over) |
132
+ (binary >> intermediate_exp.as(:first_value) >> intermediate_exp.as(:second_value)).as(:binary)
133
+ end
134
+
135
+ rule(:sequence) do
136
+ limits.as(:limits) |
137
+ (left_right.as(:left_right) >> power >> intermediate_exp.as(:supscript)) |
138
+ (left_right.as(:left_right) >> base >> intermediate_exp.as(:subscript)) |
139
+ left_right.as(:left_right) |
140
+ (over_class >> power >> intermediate_exp.as(:supscript)) |
141
+ (over_class >> base >> intermediate_exp.as(:subscript)) |
142
+ over_class |
143
+ (slash >> str("mbox") >> lparen.capture(:paren) >> read_text >> rparen).as(:unary_functions) |
144
+ (slash >> str("substack").as(:substack) >> lparen >> expression.as(:substack_value) >> rparen) |
145
+ (begining >> array_args >> expression.as(:table_data) >> ending).as(:environment) |
146
+ (begining >> expression.as(:table_data) >> ending).as(:environment) |
147
+ (slash >> environment >> intermediate_exp).as(:table_data) |
148
+ power_base |
149
+ binary_functions |
150
+ intermediate_exp
151
+ end
152
+
153
+ rule(:left_right_over) do
154
+ (str("\\left").as(:left) >>
155
+ lparen >>
156
+ expression.repeat.as(:dividend) >>
157
+ str("\\over") >>
158
+ expression.repeat.as(:divisor) >>
159
+ str("\\right").as(:right) >>
160
+ rparen)
161
+ end
162
+
163
+ rule(:over_class) do
164
+ (
165
+ (str("{") >> expression.repeat.as(:dividend) >> str("\\over") >> expression.repeat.as(:divisor) >> str("}")) |
166
+ (left_right_over.as(:left_right).as(:power) >> power >> intermediate_exp) |
167
+ (left_right_over.as(:left_right).as(:base) >> base >> intermediate_exp) |
168
+ left_right_over.as(:left_right)
169
+ ).as(:over)
170
+ end
171
+
172
+ rule(:iteration) do
173
+ (sequence.as(:sequence) >> expression.as(:expression)) | sequence
174
+ end
175
+
176
+ rule(:expression) { (iteration >> expression) | iteration }
177
+
178
+ root :expression
179
+
180
+ def arr_to_expression(array, name = nil)
181
+ type = array.first.class
182
+ array.reduce do |expression, expr_string|
183
+ name = name || expr_string.to_sym || expression.to_sym
184
+ expression = str(expression).as(name) if expression.is_a?(type)
185
+ expression | str(expr_string).as(name)
186
+ end
187
+ end
188
+
189
+ def read_text
190
+ dynamic do |_sour, context|
191
+ lparen = context.captures[:paren][:lparen].to_s
192
+ rparen = Constants::PARENTHESIS[lparen]
193
+ match("[^#{rparen}]").repeat.as(:mbox)
194
+ end
195
+ end
196
+ end
197
+ end
198
+ end
@@ -0,0 +1,25 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "parse"
4
+ require_relative "constants"
5
+ require_relative "transform"
6
+ module Plurimath
7
+ class Latex
8
+ class Parser
9
+ attr_accessor :text
10
+
11
+ def initialize(text)
12
+ @text = text.gsub(/\s/, "")
13
+ end
14
+
15
+ def parse
16
+ tree_t = Latex::Parse.new.parse(text)
17
+ tree_t = JSON.parse(tree_t.to_json, symbolize_names: true)
18
+ formula = Latex::Transform.new.apply(tree_t)
19
+ formula = [formula] unless formula.is_a?(Array)
20
+
21
+ Math::Formula.new(formula)
22
+ end
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,458 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Plurimath
4
+ class Latex
5
+ class Transform < Parslet::Transform
6
+ rule(base: simple(:base)) { base }
7
+ rule(over: simple(:over)) { over }
8
+ rule(number: simple(:num)) { Math::Number.new(num) }
9
+ rule(power: simple(:power)) { power }
10
+ rule(unary: simple(:unary)) { Utility.get_class(unary).new }
11
+ rule(operant: simple(:oper)) { Math::Symbol.new(oper) }
12
+ rule("\\\\": simple(:slash)) { Math::Symbol.new(slash) }
13
+ rule(limits: simple(:limits)) { limits }
14
+
15
+ rule(unary_functions: simple(:unary)) { unary }
16
+ rule(left_right: simple(:left_right)) { left_right }
17
+ rule(under_over: simple(:under_over)) { under_over }
18
+ rule(power_base: simple(:power_base)) { power_base }
19
+ rule(table_data: simple(:table_data)) { table_data }
20
+
21
+ rule(environment: simple(:environment)) { environment }
22
+
23
+ rule(text: simple(:text)) do
24
+ Math::Function::Text.new(text)
25
+ end
26
+
27
+ rule(binary: simple(:binary)) do
28
+ binary.is_a?(String) ? Math::Function::Text.new(binary) : binary
29
+ end
30
+
31
+ rule(symbols: simple(:sym)) do
32
+ Math::Symbol.new(
33
+ Constants::SYMBOLS[sym.to_sym] || sym,
34
+ )
35
+ end
36
+
37
+ rule(lparen: simple(:lparen),
38
+ rparen: simple(:rparen)) do
39
+ Math::Formula.new
40
+ end
41
+
42
+ rule(left_right: simple(:left_right),
43
+ subscript: simple(:subscript)) do
44
+ Math::Function::Base.new(
45
+ left_right,
46
+ subscript,
47
+ )
48
+ end
49
+
50
+ rule(left_right: simple(:left_right),
51
+ supscript: simple(:supscript)) do
52
+ Math::Function::Power.new(
53
+ left_right,
54
+ supscript,
55
+ )
56
+ end
57
+
58
+ rule(left: simple(:left),
59
+ lparen: simple(:lparen),
60
+ expression: sequence(:expr),
61
+ right: simple(:right),
62
+ rparen: simple(:rparen)) do
63
+ Math::Formula.new(
64
+ [
65
+ Math::Function::Left.new(lparen),
66
+ Math::Formula.new(expr),
67
+ Math::Function::Right.new(rparen),
68
+ ],
69
+ )
70
+ end
71
+
72
+ rule(left: simple(:left),
73
+ lparen: simple(:lparen),
74
+ expression: simple(:expr),
75
+ right: simple(:right),
76
+ rparen: simple(:rparen)) do
77
+ Math::Formula.new(
78
+ [
79
+ Math::Function::Left.new(lparen),
80
+ expr,
81
+ Math::Function::Right.new(rparen),
82
+ ],
83
+ )
84
+ end
85
+
86
+ rule(power: simple(:power),
87
+ number: simple(:number)) do
88
+ Math::Function::Power.new(
89
+ power,
90
+ Math::Number.new(number),
91
+ )
92
+ end
93
+
94
+ rule(left: simple(:left),
95
+ lparen: simple(:lparen),
96
+ dividend: subtree(:dividend),
97
+ divisor: sequence(:divisor),
98
+ right: simple(:right),
99
+ rparen: simple(:rparen)) do
100
+ Math::Formula.new(
101
+ [
102
+ Math::Function::Left.new(lparen),
103
+ Math::Function::Over.new(
104
+ Math::Formula.new(dividend.flatten),
105
+ Math::Formula.new(divisor),
106
+ ),
107
+ Math::Function::Right.new(rparen),
108
+ ],
109
+ )
110
+ end
111
+
112
+ rule(dividend: subtree(:dividend),
113
+ divisor: subtree(:divisor)) do
114
+ Math::Function::Over.new(
115
+ Math::Formula.new(dividend.flatten),
116
+ Math::Formula.new(divisor.flatten),
117
+ )
118
+ end
119
+
120
+ rule(over: simple(:over),
121
+ subscript: simple(:subscript)) do
122
+ Math::Function::Base.new(
123
+ over,
124
+ subscript,
125
+ )
126
+ end
127
+
128
+ rule(over: simple(:over),
129
+ supscript: simple(:supscript)) do
130
+ Math::Function::Power.new(
131
+ over,
132
+ supscript,
133
+ )
134
+ end
135
+
136
+ rule(operant: simple(:operant),
137
+ subscript: simple(:subscript)) do
138
+ Math::Function::Base.new(
139
+ Math::Symbol.new(operant),
140
+ subscript,
141
+ )
142
+ end
143
+
144
+ rule(sequence: simple(:sequence),
145
+ expression: simple(:expr)) do
146
+ [sequence, expr]
147
+ end
148
+
149
+ rule(sequence: simple(:sequence),
150
+ expression: sequence(:expr)) do
151
+ [sequence] + expr
152
+ end
153
+
154
+ rule(unary_functions: simple(:unary),
155
+ subscript: simple(:subscript)) do
156
+ Math::Function::Base.new(
157
+ unary,
158
+ subscript,
159
+ )
160
+ end
161
+
162
+ rule(fonts: simple(:fonts),
163
+ intermediate_exp: simple(:int_exp)) do
164
+ if Utility::FONT_STYLES[fonts.to_sym]
165
+ Utility::FONT_STYLES[fonts.to_sym].new(
166
+ int_exp,
167
+ fonts,
168
+ )
169
+ else
170
+ Math::Function::FontStyle.new(
171
+ int_exp,
172
+ fonts,
173
+ )
174
+ end
175
+ end
176
+
177
+ rule(number: simple(:number),
178
+ subscript: simple(:subscript)) do
179
+ Math::Function::Base.new(
180
+ Math::Number.new(number),
181
+ subscript,
182
+ )
183
+ end
184
+
185
+ rule(symbols: simple(:sym),
186
+ subscript: simple(:subscript)) do
187
+ Math::Function::Base.new(
188
+ Math::Symbol.new(
189
+ Constants::SYMBOLS[sym.to_sym] || sym,
190
+ ),
191
+ subscript,
192
+ )
193
+ end
194
+
195
+ rule(symbols: simple(:sym),
196
+ supscript: simple(:supscript)) do
197
+ Math::Function::Power.new(
198
+ Math::Symbol.new(
199
+ Constants::SYMBOLS[sym.to_sym] || sym,
200
+ ),
201
+ supscript,
202
+ )
203
+ end
204
+
205
+ rule(text: simple(:text),
206
+ subscript: simple(:subscript)) do
207
+ Math::Function::Base.new(
208
+ Math::Function::Text.new(text),
209
+ subscript,
210
+ )
211
+ end
212
+
213
+ rule(text: simple(:text),
214
+ supscript: simple(:supscript)) do
215
+ Math::Function::Power.new(
216
+ Math::Function::Text.new(text),
217
+ supscript,
218
+ )
219
+ end
220
+
221
+ rule(unary: simple(:unary),
222
+ first_value: simple(:first_value)) do
223
+ Utility.get_class(
224
+ unary == "overline" ? "bar" : unary,
225
+ ).new(first_value)
226
+ end
227
+
228
+ rule(sqrt: simple(:sqrt),
229
+ intermediate_exp: simple(:int_exp)) do
230
+ Math::Function::Sqrt.new(int_exp)
231
+ end
232
+
233
+ rule(fonts: simple(:fonts),
234
+ intermediate_exp: simple(:int_exp),
235
+ supscript: simple(:supscript)) do
236
+ font_style = if Utility::FONT_STYLES[fonts.to_sym].nil?
237
+ Math::Function::FontStyle.new(
238
+ int_exp,
239
+ fonts,
240
+ )
241
+ else
242
+ Utility::FONT_STYLES[fonts.to_sym].new(
243
+ int_exp,
244
+ fonts,
245
+ )
246
+ end
247
+ Math::Function::Power.new(
248
+ font_style,
249
+ supscript,
250
+ )
251
+ end
252
+
253
+ rule(fonts: simple(:fonts),
254
+ intermediate_exp: simple(:int_exp),
255
+ subscript: simple(:subscript)) do
256
+ font_style = if Utility::FONT_STYLES[fonts.to_sym].nil?
257
+ Math::Function::FontStyle.new(
258
+ int_exp,
259
+ fonts,
260
+ )
261
+ else
262
+ Utility::FONT_STYLES[fonts.to_sym].new(
263
+ int_exp,
264
+ fonts,
265
+ )
266
+ end
267
+ Math::Function::Base.new(
268
+ font_style,
269
+ subscript,
270
+ )
271
+ end
272
+
273
+ rule(root: simple(:root),
274
+ first_value: simple(:first_value),
275
+ second_value: simple(:second_value)) do
276
+ Math::Function::Root.new(
277
+ first_value,
278
+ second_value,
279
+ )
280
+ end
281
+
282
+ rule(unary_functions: simple(:unary),
283
+ base: simple(:base),
284
+ power: simple(:power)) do
285
+ Math::Function::Limits.new(
286
+ Utility.get_class(unary).new,
287
+ base,
288
+ power,
289
+ )
290
+ end
291
+
292
+ rule(lparen: simple(:lparen),
293
+ mbox: simple(:mbox),
294
+ rparen: simple(:rparen)) do
295
+ Math::Function::Text.new("\\mbox{#{mbox}}")
296
+ end
297
+
298
+ rule(lparen: simple(:lparen),
299
+ symbols: simple(:sym),
300
+ rparen: simple(:rparen)) do
301
+ Math::Symbol.new(
302
+ Constants::SYMBOLS[sym.to_sym] || sym,
303
+ )
304
+ end
305
+
306
+ rule(lparen: simple(:lparen),
307
+ expression: simple(:expr),
308
+ rparen: simple(:rparen)) do
309
+ expr
310
+ end
311
+
312
+ rule(lparen: simple(:lparen),
313
+ expression: sequence(:expr),
314
+ rparen: simple(:rparen)) do
315
+ Math::Formula.new(expr)
316
+ end
317
+
318
+ rule(lparen: simple(:lparen),
319
+ expression: simple(:expr),
320
+ rparen: simple(:rparen),
321
+ supscript: simple(:supscript)) do
322
+ Math::Function::Power.new(
323
+ Math::Formula.new(expr),
324
+ supscript,
325
+ )
326
+ end
327
+
328
+ rule(lparen: simple(:lparen),
329
+ expression: simple(:expr),
330
+ rparen: simple(:rparen),
331
+ subscript: simple(:subscript)) do
332
+ Math::Function::Base.new(
333
+ Math::Formula.new(expr),
334
+ subscript,
335
+ )
336
+ end
337
+
338
+ rule(binary: simple(:binary),
339
+ subscript: simple(:subscript),
340
+ supscript: simple(:supscript)) do
341
+ Utility.get_class(binary).new(
342
+ subscript,
343
+ supscript,
344
+ )
345
+ end
346
+
347
+ rule(binary: simple(:binary),
348
+ subscript: simple(:subscript)) do
349
+ Utility.get_class(binary).new(subscript)
350
+ end
351
+
352
+ rule(text: simple(:text),
353
+ subscript: simple(:subscript),
354
+ supscript: simple(:supscript)) do
355
+ Math::Function::PowerBase.new(
356
+ Math::Function::Text.new(text),
357
+ subscript,
358
+ supscript,
359
+ )
360
+ end
361
+
362
+ rule(symbols: simple(:sym),
363
+ subscript: simple(:subscript),
364
+ supscript: simple(:supscript)) do
365
+ Math::Function::PowerBase.new(
366
+ Math::Symbol.new(
367
+ Constants::SYMBOLS[sym.to_sym] || sym,
368
+ ),
369
+ subscript,
370
+ supscript,
371
+ )
372
+ end
373
+
374
+ rule(binary: simple(:binary),
375
+ first_value: simple(:first_value),
376
+ second_value: simple(:second_value)) do
377
+ if binary == "binom"
378
+ Math::Function::Table.new(
379
+ [
380
+ Math::Function::Tr.new([first_value]),
381
+ Math::Function::Tr.new([second_value]),
382
+ ],
383
+ "(",
384
+ ")",
385
+ )
386
+ else
387
+ Utility.get_class(
388
+ binary.include?("mod") ? "mod" : binary,
389
+ ).new(
390
+ first_value,
391
+ second_value,
392
+ )
393
+ end
394
+ end
395
+
396
+ rule(begining: simple(:begining),
397
+ table_data: sequence(:table_data),
398
+ ending: simple(:ending)) do
399
+ Utility.get_table_class(begining).new(
400
+ Utility.organize_table(table_data),
401
+ )
402
+ end
403
+
404
+ rule(begining: simple(:begining),
405
+ args: simple(:args),
406
+ table_data: simple(:table_data),
407
+ ending: simple(:ending)) do
408
+ Utility.get_table_class(begining).new(
409
+ Utility.organize_table([table_data]),
410
+ nil,
411
+ [args],
412
+ )
413
+ end
414
+
415
+ rule(begining: simple(:begining),
416
+ args: sequence(:args),
417
+ table_data: sequence(:table_data),
418
+ ending: simple(:ending)) do
419
+ Utility.get_table_class(begining).new(
420
+ Utility.organize_table(table_data),
421
+ nil,
422
+ args,
423
+ )
424
+ end
425
+
426
+ rule(begining: simple(:begining),
427
+ args: simple(:args),
428
+ table_data: sequence(:table_data),
429
+ ending: simple(:ending)) do
430
+ Utility.get_table_class(begining).new(
431
+ Utility.organize_table(table_data),
432
+ nil,
433
+ [args],
434
+ )
435
+ end
436
+
437
+ rule(environment: simple(:env),
438
+ lparen: simple(:lparen),
439
+ expression: sequence(:expr),
440
+ rparen: simple(:rparen)) do
441
+ left_paren = Constants::MATRICES[env.to_sym]
442
+ Math::Function::Table.new(
443
+ Utility.organize_table(expr),
444
+ left_paren,
445
+ Constants::PARENTHESIS[left_paren],
446
+ )
447
+ end
448
+
449
+ rule(lparen: simple(:lparen),
450
+ expression: sequence(:expr),
451
+ rparen: simple(:rparen),
452
+ supscript: simple(:supscript)) do
453
+ formula = Math::Formula.new(expr)
454
+ Math::Function::Power.new(formula, supscript)
455
+ end
456
+ end
457
+ end
458
+ end
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Plurimath
4
+ class Latex
5
+ attr_accessor :text
6
+
7
+ def initialize(text)
8
+ @text = text
9
+ end
10
+
11
+ def to_formula
12
+ Parser.new(text).parse
13
+ end
14
+ end
15
+ end