mathai 0.7.7__tar.gz → 0.7.8__tar.gz
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.
- {mathai-0.7.7 → mathai-0.7.8}/PKG-INFO +1 -1
- {mathai-0.7.7 → mathai-0.7.8}/mathai/__init__.py +2 -2
- {mathai-0.7.7 → mathai-0.7.8}/mathai/base.py +0 -1
- mathai-0.7.8/mathai/diff.py +156 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/integrate.py +1 -1
- mathai-0.7.8/mathai/ode.py +266 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/parser.py +2 -3
- mathai-0.7.8/mathai/pde.py +105 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai.egg-info/PKG-INFO +1 -1
- {mathai-0.7.7 → mathai-0.7.8}/setup.py +1 -1
- mathai-0.7.7/mathai/diff.py +0 -74
- mathai-0.7.7/mathai/ode.py +0 -189
- mathai-0.7.7/mathai/pde.py +0 -139
- {mathai-0.7.7 → mathai-0.7.8}/README.md +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/apart.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/bivariate_inequality.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/console.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/expand.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/factor.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/fraction.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/inverse.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/limit.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/linear.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/logic.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/matrix.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/parsetab.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/printeq.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/simplify.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/statistics.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/structure.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/tool.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/trig.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai/univariate_inequality.py +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai.egg-info/SOURCES.txt +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai.egg-info/dependency_links.txt +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai.egg-info/requires.txt +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/mathai.egg-info/top_level.txt +0 -0
- {mathai-0.7.7 → mathai-0.7.8}/setup.cfg +0 -0
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
from .ode import diffsolve as ode_solve
|
|
2
2
|
from .ode import diffsolve_sep as ode_shift_term
|
|
3
3
|
|
|
4
|
-
from .pde import pde_sep, want
|
|
4
|
+
from .pde import pde_sep, want, absorb
|
|
5
5
|
|
|
6
6
|
from .linear import linear_solve, linear_or
|
|
7
7
|
|
|
@@ -21,7 +21,7 @@ from .integrate import rm_const as integrate_const
|
|
|
21
21
|
from .integrate import solve_integrate as integrate_clean
|
|
22
22
|
from .integrate import integrate_formula
|
|
23
23
|
|
|
24
|
-
from .diff import diff
|
|
24
|
+
from .diff import diff, diff2
|
|
25
25
|
|
|
26
26
|
from .factor import factor as factor1
|
|
27
27
|
from .factor import factor2, factor3
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
from .trig import trig0
|
|
2
|
+
from .simplify import simplify
|
|
3
|
+
from .base import *
|
|
4
|
+
|
|
5
|
+
def helper(eq):
|
|
6
|
+
name = eq.name
|
|
7
|
+
if name in ["f_dif", "f_pdif"]:
|
|
8
|
+
if eq.children[0].name == "f_add":
|
|
9
|
+
return summation([TreeNode(name, [child, eq.children[1]]) for child in eq.children[0].children])
|
|
10
|
+
|
|
11
|
+
if eq.children[0].name == "f_mul":
|
|
12
|
+
return summation([product([TreeNode(name, [child, eq.children[1]]) if index==index2 else child for index2, child in enumerate(eq.children[0].children)])\
|
|
13
|
+
for index in range(len(eq.children[0].children))])
|
|
14
|
+
if eq.children[0].name == "f_pow" and "v_" not in str_form(eq.children[0].children[1]):
|
|
15
|
+
base, power = eq.children[0].children
|
|
16
|
+
dbase = TreeNode(name, [base, eq.children[1]])
|
|
17
|
+
b1 = power - tree_form("d_1")
|
|
18
|
+
bab1 = TreeNode("f_pow", [base, b1])
|
|
19
|
+
return power * bab1 * dbase
|
|
20
|
+
|
|
21
|
+
if eq.children[0].name == "f_pow":
|
|
22
|
+
a, b = eq.children
|
|
23
|
+
return a**b * ((b/a) * TreeNode(name, [a, eq.children[1]]) + a.fx("log") * TreeNode(name, [b, eq.children[1]]))
|
|
24
|
+
|
|
25
|
+
if "v_" not in str_form(eq.children[0]):
|
|
26
|
+
return tree_form("d_0")
|
|
27
|
+
|
|
28
|
+
if eq.children[0] == eq.children[1]:
|
|
29
|
+
return tree_form("d_1")
|
|
30
|
+
|
|
31
|
+
if name == "f_pdif" and not contain(eq.children[0], eq.children[1]):
|
|
32
|
+
return tree_form("d_0")
|
|
33
|
+
if eq.children[0].name == "f_sin":
|
|
34
|
+
eq.children[0].name = "f_cos"
|
|
35
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
36
|
+
return d*eq.children[0]
|
|
37
|
+
if eq.children[0].name == "f_cos":
|
|
38
|
+
eq.children[0].name = "f_sin"
|
|
39
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
40
|
+
return tree_form("d_-1")*d*eq.children[0]
|
|
41
|
+
if eq.children[0].name == "f_tan":
|
|
42
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
43
|
+
return d/(eq.children[0].children[0].fx("cos")*eq.children[0].children[0].fx("cos"))
|
|
44
|
+
if eq.children[0].name == "f_log":
|
|
45
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
46
|
+
return d*(tree_form("d_1")/eq.children[0].children[0])
|
|
47
|
+
if eq.children[0].name == "f_arcsin":
|
|
48
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
49
|
+
return d/(tree_form("d_1")-eq.children[0].children[0]*eq.children[0].children[0])**(tree_form("d_2")**-1)
|
|
50
|
+
if eq.children[0].name == "f_arccos":
|
|
51
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
52
|
+
return tree_form("d_-1")*d/(tree_form("d_1")-eq.children[0].children[0]*eq.children[0].children[0])**(tree_form("d_2")**-1)
|
|
53
|
+
if eq.children[0].name == "f_arctan":
|
|
54
|
+
d = TreeNode(name, [eq.children[0].children[0], eq.children[1]])
|
|
55
|
+
return d/(tree_form("d_1")+eq.children[0].children[0]*eq.children[0].children[0])
|
|
56
|
+
|
|
57
|
+
return eq
|
|
58
|
+
|
|
59
|
+
def diff3(eq):
|
|
60
|
+
eq = simplify(eq)
|
|
61
|
+
|
|
62
|
+
stack = [(eq, False)]
|
|
63
|
+
out = {}
|
|
64
|
+
|
|
65
|
+
while stack:
|
|
66
|
+
node, visited = stack.pop()
|
|
67
|
+
|
|
68
|
+
if not visited:
|
|
69
|
+
stack.append((node, True))
|
|
70
|
+
for c in node.children:
|
|
71
|
+
stack.append((c, False))
|
|
72
|
+
continue
|
|
73
|
+
|
|
74
|
+
new_children = [out[c] for c in node.children]
|
|
75
|
+
rebuilt = TreeNode(node.name, new_children)
|
|
76
|
+
rebuilt = helper(rebuilt)
|
|
77
|
+
rebuilt = simplify(rebuilt)
|
|
78
|
+
|
|
79
|
+
out[node] = rebuilt
|
|
80
|
+
|
|
81
|
+
return out[eq]
|
|
82
|
+
|
|
83
|
+
def diff2(eq):
|
|
84
|
+
return dowhile(eq, diff3)
|
|
85
|
+
def diff(equation, var="v_0"):
|
|
86
|
+
def diffeq(eq):
|
|
87
|
+
eq = simplify(eq)
|
|
88
|
+
if "v_" not in str_form(eq):
|
|
89
|
+
return tree_form("d_0")
|
|
90
|
+
if eq.name == "f_add":
|
|
91
|
+
add = tree_form("d_0")
|
|
92
|
+
for child in eq.children:
|
|
93
|
+
add += diffeq(child)
|
|
94
|
+
return add
|
|
95
|
+
elif eq.name == "f_abs":
|
|
96
|
+
return diffeq(eq.children[0])*eq.children[0]/eq
|
|
97
|
+
elif eq.name == "f_pow" and eq.children[0].name == "s_e":
|
|
98
|
+
return diffeq(eq.children[1])*eq
|
|
99
|
+
elif eq.name == "f_tan":
|
|
100
|
+
return diffeq(eq.children[0])/(eq.children[0].fx("cos")*eq.children[0].fx("cos"))
|
|
101
|
+
elif eq.name == "f_log":
|
|
102
|
+
return diffeq(eq.children[0])*(tree_form("d_1")/eq.children[0])
|
|
103
|
+
elif eq.name == "f_arcsin":
|
|
104
|
+
return diffeq(eq.children[0])/(tree_form("d_1")-eq.children[0]*eq.children[0])**(tree_form("d_2")**-1)
|
|
105
|
+
elif eq.name == "f_arccos":
|
|
106
|
+
return tree_form("d_-1")*diffeq(eq.children[0])/(tree_form("d_1")-eq.children[0]*eq.children[0])**(tree_form("d_2")**-1)
|
|
107
|
+
elif eq.name == "f_arctan":
|
|
108
|
+
return diffeq(eq.children[0])/(tree_form("d_1")+eq.children[0]*eq.children[0])
|
|
109
|
+
elif eq.name == "f_pow" and "v_" in str_form(eq.children[1]):
|
|
110
|
+
a, b = eq.children
|
|
111
|
+
return a**b * ((b/a) * diffeq(a) + a.fx("log") * diffeq(b))
|
|
112
|
+
elif eq.name == "f_mul":
|
|
113
|
+
add = tree_form("d_0")
|
|
114
|
+
for i in range(len(eq.children)):
|
|
115
|
+
tmp = eq.children.pop(i)
|
|
116
|
+
if len(eq.children)==1:
|
|
117
|
+
eq2 = eq.children[0]
|
|
118
|
+
else:
|
|
119
|
+
eq2 = eq
|
|
120
|
+
add += diffeq(tmp)*eq2
|
|
121
|
+
eq.children.insert(i, tmp)
|
|
122
|
+
return add
|
|
123
|
+
elif eq.name == "f_sin":
|
|
124
|
+
eq.name = "f_cos"
|
|
125
|
+
return diffeq(eq.children[0])*eq
|
|
126
|
+
elif eq.name == "f_cos":
|
|
127
|
+
eq.name = "f_sin"
|
|
128
|
+
return tree_form("d_-1")*diffeq(eq.children[0])*eq
|
|
129
|
+
elif eq.name[:2] == "v_":
|
|
130
|
+
return TreeNode("f_dif", [eq])
|
|
131
|
+
elif eq.name == "f_pow" and "v_" not in str_form(eq.children[1]):
|
|
132
|
+
base, power = eq.children
|
|
133
|
+
dbase = diffeq(base)
|
|
134
|
+
b1 = power - tree_form("d_1")
|
|
135
|
+
bab1 = TreeNode("f_pow", [base, b1])
|
|
136
|
+
return power * bab1 * dbase
|
|
137
|
+
return TreeNode("f_dif", [eq, tree_form(var)])
|
|
138
|
+
def helper2(equation, var="v_0"):
|
|
139
|
+
if equation.name == "f_dif":
|
|
140
|
+
if equation.children[0].name == var:
|
|
141
|
+
return tree_form("d_1")
|
|
142
|
+
if var not in str_form(equation.children[0]):
|
|
143
|
+
return tree_form("d_0")
|
|
144
|
+
else:
|
|
145
|
+
return equation
|
|
146
|
+
return TreeNode(equation.name, [helper2(child, var) for child in equation.children])
|
|
147
|
+
def calc(eq):
|
|
148
|
+
if eq.name == "f_dif":
|
|
149
|
+
return diffeq(trig0(eq.children[0]))
|
|
150
|
+
return TreeNode(eq.name, [calc(child) for child in eq.children])
|
|
151
|
+
if var is None:
|
|
152
|
+
return simplify(calc(equation))
|
|
153
|
+
equation = diffeq(trig0(equation))
|
|
154
|
+
equation = helper2(equation, var)
|
|
155
|
+
return simplify(equation)
|
|
156
|
+
|
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
from collections import Counter
|
|
2
|
+
from .diff import diff
|
|
3
|
+
from .factor import factor, factor2
|
|
4
|
+
from .expand import expand
|
|
5
|
+
from .base import *
|
|
6
|
+
from .fraction import fraction
|
|
7
|
+
from .simplify import simplify
|
|
8
|
+
import copy
|
|
9
|
+
from .inverse import inverse
|
|
10
|
+
from .parser import parse
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
def jjj(lhs, rhs):
|
|
14
|
+
lst = [lhs, rhs]
|
|
15
|
+
for i in range(2):
|
|
16
|
+
if lst[i].name in ["f_mul", "f_add"]:
|
|
17
|
+
|
|
18
|
+
out = []
|
|
19
|
+
for child in lst[i].children:
|
|
20
|
+
|
|
21
|
+
if not contain(child, tree_form(f"v_{i}")):
|
|
22
|
+
out.append(child)
|
|
23
|
+
if out == []:
|
|
24
|
+
continue
|
|
25
|
+
out = TreeNode(lst[i].name, out)
|
|
26
|
+
|
|
27
|
+
if len(out.children) == 1:
|
|
28
|
+
out = out.children[0]
|
|
29
|
+
out = out.copy_tree()
|
|
30
|
+
if lst[i].name == "f_add":
|
|
31
|
+
lst[i] = lst[i] - out
|
|
32
|
+
lst[1-i] = lst[1-i] - out
|
|
33
|
+
else:
|
|
34
|
+
lst[i] = lst[i] / out
|
|
35
|
+
lst[1-i] = lst[1-i] / out
|
|
36
|
+
|
|
37
|
+
lst = [simplify(expand(simplify(item))) for item in lst]
|
|
38
|
+
return lst
|
|
39
|
+
|
|
40
|
+
def kkk(lhs, rhs, depth=3):
|
|
41
|
+
|
|
42
|
+
lst = jjj(lhs, rhs)
|
|
43
|
+
|
|
44
|
+
if depth < 0:
|
|
45
|
+
return lst, False
|
|
46
|
+
if not contain(lst[0], tree_form("v_1")) and not contain(lst[1], tree_form("v_0")):
|
|
47
|
+
return lst, True
|
|
48
|
+
orig = copy.deepcopy(lst)
|
|
49
|
+
for i in range(2):
|
|
50
|
+
if lst[i].name in ["f_mul", "f_add"]:
|
|
51
|
+
for child in lst[i].children:
|
|
52
|
+
|
|
53
|
+
out = child
|
|
54
|
+
if lst[i].name == "f_add":
|
|
55
|
+
lst[i] = lst[i] - out
|
|
56
|
+
lst[1-i] = lst[1-i] - out
|
|
57
|
+
else:
|
|
58
|
+
lst[i] = lst[i] / out
|
|
59
|
+
lst[1-i] = lst[1-i] / out
|
|
60
|
+
lst = [simplify(item) for item in lst]
|
|
61
|
+
|
|
62
|
+
output = kkk(lst[0], lst[1], depth-1)
|
|
63
|
+
lst = orig
|
|
64
|
+
if output[1]:
|
|
65
|
+
return output
|
|
66
|
+
return lst, False
|
|
67
|
+
|
|
68
|
+
def inversediff(lhs, rhs):
|
|
69
|
+
out = [[tree_form("d_0"), lhs-rhs], False]
|
|
70
|
+
while True:
|
|
71
|
+
out = list(kkk(out[0][0], out[0][1]))
|
|
72
|
+
if out[1]:
|
|
73
|
+
break
|
|
74
|
+
out[0] = [simplify(item) for item in out[0]]
|
|
75
|
+
|
|
76
|
+
out = out[0]
|
|
77
|
+
return simplify(e0(out[0]-out[1]))
|
|
78
|
+
|
|
79
|
+
def allocvar():
|
|
80
|
+
return tree_form("v_101")
|
|
81
|
+
|
|
82
|
+
def epowersplit(eq):
|
|
83
|
+
if eq.name == "f_pow" and eq.children[1].name == "f_add":
|
|
84
|
+
return product([eq.children[0]**child for child in eq.children[1].children])
|
|
85
|
+
return TreeNode(eq.name, [epowersplit(child) for child in eq.children])
|
|
86
|
+
def esolve(s):
|
|
87
|
+
if s.name == "f_add" and "f_log" in str_form(s):
|
|
88
|
+
return product([tree_form("s_e")**child for child in s.children]) - tree_form("d_1")
|
|
89
|
+
return TreeNode(s.name, [esolve(child) for child in s.children])
|
|
90
|
+
def diffsolve_sep2(eq):
|
|
91
|
+
global tab
|
|
92
|
+
|
|
93
|
+
s = []
|
|
94
|
+
eq = simplify(expand(eq))
|
|
95
|
+
eq = e1(eq)
|
|
96
|
+
|
|
97
|
+
def vlor1(eq):
|
|
98
|
+
if contain(eq, tree_form("v_0")) and not contain(eq, tree_form("v_1")):
|
|
99
|
+
return True
|
|
100
|
+
if contain(eq, tree_form("v_1")) and not contain(eq, tree_form("v_0")):
|
|
101
|
+
return True
|
|
102
|
+
return False
|
|
103
|
+
if eq.name == "f_add" and all(vlor1(child) and [str_form(x) for x in factor_generation(copy.deepcopy(child))].count(str_form(tree_form(vlist(child)[0]).fx("dif")))==1 for child in eq.children):
|
|
104
|
+
for child in eq.children:
|
|
105
|
+
v = vlist(child)[0]
|
|
106
|
+
v2 = tree_form(v).fx("dif")
|
|
107
|
+
child = replace(child, v2, tree_form("d_1"))
|
|
108
|
+
child = simplify(child)
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
tmp6 = TreeNode("f_integrate", [child, tree_form(v)])
|
|
112
|
+
s.append(tmp6)
|
|
113
|
+
|
|
114
|
+
if s[-1] is None:
|
|
115
|
+
return None
|
|
116
|
+
s.append(allocvar())
|
|
117
|
+
else:
|
|
118
|
+
return None
|
|
119
|
+
s = summation(s)
|
|
120
|
+
s = simplify(e0(s))
|
|
121
|
+
|
|
122
|
+
return groupe(s)
|
|
123
|
+
def e0(eq):
|
|
124
|
+
return TreeNode("f_eq", [eq, tree_form("d_0")])
|
|
125
|
+
def e1(eq):
|
|
126
|
+
if eq.name == "f_eq":
|
|
127
|
+
eq = eq.children[0]
|
|
128
|
+
return eq
|
|
129
|
+
def groupe(eq):
|
|
130
|
+
eq = esolve(eq)
|
|
131
|
+
eq = simplify(eq)
|
|
132
|
+
eq = fraction(eq)
|
|
133
|
+
eq = simplify(eq)
|
|
134
|
+
eq = epowersplit(eq)
|
|
135
|
+
return eq
|
|
136
|
+
|
|
137
|
+
def diffsolve_sep(eq):
|
|
138
|
+
eq = epowersplit(eq)
|
|
139
|
+
eq = inversediff(tree_form("d_0"), eq.children[0].copy_tree())
|
|
140
|
+
return eq
|
|
141
|
+
|
|
142
|
+
def diffsolve(eq):
|
|
143
|
+
orig = eq.copy_tree()
|
|
144
|
+
if order(eq) == 2:
|
|
145
|
+
for i in range(2):
|
|
146
|
+
out = second_order_dif(eq, tree_form(f"v_{i}"), tree_form(f"v_{1-i}"))
|
|
147
|
+
if out is not None:
|
|
148
|
+
return out
|
|
149
|
+
return orig
|
|
150
|
+
|
|
151
|
+
eq = diffsolve_sep2(diffsolve_sep(eq))
|
|
152
|
+
if eq is None:
|
|
153
|
+
for i in range(2):
|
|
154
|
+
a = tree_form(f"v_{i}")
|
|
155
|
+
b = tree_form(f"v_{1-i}")
|
|
156
|
+
c = tree_form("v_2")
|
|
157
|
+
eq2 = replace(orig, b,b*a)
|
|
158
|
+
eq2 = replace(eq2, (a*b).fx("dif"), a.fx("dif")*b + b.fx("dif")*a)
|
|
159
|
+
eq2 = expand(simplify(fraction(simplify(eq2))))
|
|
160
|
+
eq2 = diffsolve_sep(eq2)
|
|
161
|
+
eq2 = diffsolve_sep2(eq2)
|
|
162
|
+
if eq2 is not None:
|
|
163
|
+
return e0(TreeNode("f_subs", [replace(eq2.children[0],b,c), c,b/a]).fx("try"))
|
|
164
|
+
eq = orig
|
|
165
|
+
|
|
166
|
+
eq = fraction(eq)
|
|
167
|
+
eq = simplify(eq)
|
|
168
|
+
for i in range(2):
|
|
169
|
+
|
|
170
|
+
out = linear_dif(eq, tree_form(f"v_{i}"), tree_form(f"v_{1-i}"))
|
|
171
|
+
if out is not None:
|
|
172
|
+
return out
|
|
173
|
+
return eq
|
|
174
|
+
def clist(x):
|
|
175
|
+
return list(x.elements())
|
|
176
|
+
def collect_term(eq, term_lst):
|
|
177
|
+
|
|
178
|
+
lst = None
|
|
179
|
+
if eq.name == "f_add":
|
|
180
|
+
lst = copy.deepcopy(eq.children)
|
|
181
|
+
else:
|
|
182
|
+
lst = [eq]
|
|
183
|
+
|
|
184
|
+
other = []
|
|
185
|
+
dic = {}
|
|
186
|
+
term_lst = list(sorted(term_lst, key=lambda x: -len(factor_generation(x))))
|
|
187
|
+
for item in term_lst:
|
|
188
|
+
dic[item] = tree_form("d_0")
|
|
189
|
+
for item2 in lst:
|
|
190
|
+
done = True
|
|
191
|
+
tmp2 = Counter(factor_generation(item2))
|
|
192
|
+
for index, item in enumerate(term_lst):
|
|
193
|
+
|
|
194
|
+
tmp = Counter(factor_generation(item))
|
|
195
|
+
|
|
196
|
+
if (tmp2&tmp) == tmp:
|
|
197
|
+
if item in dic.keys():
|
|
198
|
+
|
|
199
|
+
dic[item] += product(clist(tmp2-tmp))
|
|
200
|
+
else:
|
|
201
|
+
|
|
202
|
+
dic[item] = product(clist(tmp2-tmp))
|
|
203
|
+
done = False
|
|
204
|
+
break
|
|
205
|
+
if done:
|
|
206
|
+
other.append(item2)
|
|
207
|
+
other = summation(other)
|
|
208
|
+
|
|
209
|
+
for key in dic.keys():
|
|
210
|
+
dic[key] = simplify(dic[key])
|
|
211
|
+
return [dic, simplify(other)]
|
|
212
|
+
def order(eq,m=0):
|
|
213
|
+
best = m
|
|
214
|
+
if eq.name in ["f_pdif", "f_dif"]:
|
|
215
|
+
out = order(eq.children[0], m+1)
|
|
216
|
+
best = max(out, best)
|
|
217
|
+
else:
|
|
218
|
+
for child in eq.children:
|
|
219
|
+
out = order(child, m)
|
|
220
|
+
best = max(out, best)
|
|
221
|
+
return best
|
|
222
|
+
def second_order_dif(eq, a, b):
|
|
223
|
+
eq = simplify(eq)
|
|
224
|
+
nn = [TreeNode("f_dif", [TreeNode("f_dif", [b,a]),a]), TreeNode("f_dif", [b,a]), b]
|
|
225
|
+
out = collect_term(eq.children[0], nn)
|
|
226
|
+
if out[1] == tree_form("d_0"):
|
|
227
|
+
tmp = out[0][nn[0]]
|
|
228
|
+
if tmp != tree_form("d_0"):
|
|
229
|
+
for key in out[0].keys():
|
|
230
|
+
out[0][key] = simplify(out[0][key]/tmp)
|
|
231
|
+
|
|
232
|
+
B = out[0][nn[1]]
|
|
233
|
+
C = out[0][nn[2]]
|
|
234
|
+
|
|
235
|
+
if all(all(not contain(item, item2) for item2 in [a,b]) for item in [B, C]):
|
|
236
|
+
r = parse("r")
|
|
237
|
+
s = simplify(factor2(simplify(TreeNode("f_eq", [r**2 + B*r + C, tree_form("d_0")])), True))
|
|
238
|
+
r1, r2 = [inverse(item, r.name) for item in s.children[0].children]
|
|
239
|
+
out = None
|
|
240
|
+
if contain(r1, tree_form("s_i")):
|
|
241
|
+
real = simplify(fraction((r1+r2)/tree_form("d_2")))
|
|
242
|
+
imagine = simplify((r1-real)/tree_form("s_i"))
|
|
243
|
+
out = tree_form("s_e")**(real*a)*(tree_form("v_101")*(imagine*a).fx("cos")+tree_form("v_102")*(imagine*a).fx("sin"))
|
|
244
|
+
elif fraction(simplify(r1-r2)) == tree_form("d_0"):
|
|
245
|
+
out =(tree_form("v_101")+tree_form("v_102")*a)*tree_form("s_e")**(r1*a)
|
|
246
|
+
else:
|
|
247
|
+
out = tree_form("v_101")*tree_form("s_e")**(r1*a) + tree_form("v_102")*tree_form("s_e")**(r2*a)
|
|
248
|
+
return TreeNode("f_eq", [b, out])
|
|
249
|
+
return None
|
|
250
|
+
|
|
251
|
+
def linear_dif(eq, a, b):
|
|
252
|
+
eq = simplify(eq)
|
|
253
|
+
|
|
254
|
+
out = collect_term(eq.children[0], [b.fx("dif"), b*a.fx("dif"), a.fx("dif")])
|
|
255
|
+
|
|
256
|
+
if out[1] == tree_form("d_0"):
|
|
257
|
+
tmp = out[0][b.fx("dif")]
|
|
258
|
+
if tmp != tree_form("d_0"):
|
|
259
|
+
|
|
260
|
+
for key in out[0].keys():
|
|
261
|
+
out[0][key] = simplify(out[0][key]/tmp)
|
|
262
|
+
p, q = out[0][b*a.fx("dif")], -out[0][a.fx("dif")]
|
|
263
|
+
|
|
264
|
+
f = tree_form("s_e") ** TreeNode("f_integrate", [p, a])
|
|
265
|
+
return simplify(TreeNode("f_eq", [b*f, TreeNode("f_integrate", [q*f, a])+allocvar()]))
|
|
266
|
+
return None
|
|
@@ -60,7 +60,7 @@ grammar = """
|
|
|
60
60
|
| ESCAPED_STRING -> string
|
|
61
61
|
| CAPITAL_ID -> matrix
|
|
62
62
|
|
|
63
|
-
FUNC_NAME: "midpoint" | "ref" | "expect" | "covariance" | "variance" | "subs" | "try" | "limit" | "forall" | "limitpinf" | "imply" | "exist" | "len" | "sum" | "angle" | "line" | "sum2" | "charge" | "electricfield" | "perm" | "point" | "equationrhs" | "transpose" | "equationlhs" | "equation" | "error" | "covariance" | "variance" | "expect" | "mag" | "rad" | "laplace" | "diverge" | "pdif" | "gradient" | "curl" | "point1" | "point2" | "dot" | "point3" | "line1" | "line2" | "line3" | "sin" | "circumcenter" | "eqtri" | "linesegment" | "cos" | "tan" | "log" | "sqrt" | "integrate" | "dif" | "abs" | "cosec" | "sec" | "cot" | "arctan" | "arcsin" | "arccos" | "log10"
|
|
63
|
+
FUNC_NAME: "midpoint" | "ref" | "expect" | "U" | "covariance" | "variance" | "subs" | "try" | "limit" | "forall" | "limitpinf" | "imply" | "exist" | "len" | "sum" | "angle" | "line" | "sum2" | "charge" | "electricfield" | "perm" | "point" | "equationrhs" | "transpose" | "equationlhs" | "equation" | "error" | "covariance" | "variance" | "expect" | "mag" | "rad" | "laplace" | "diverge" | "pdif" | "gradient" | "curl" | "point1" | "point2" | "dot" | "point3" | "line1" | "line2" | "line3" | "sin" | "circumcenter" | "eqtri" | "linesegment" | "cos" | "tan" | "log" | "sqrt" | "integrate" | "dif" | "abs" | "cosec" | "sec" | "cot" | "arctan" | "arcsin" | "arccos" | "log10"
|
|
64
64
|
|
|
65
65
|
VARIABLE: /[a-z]/ | "nabla" | "pi" | "kc" | "hbar" | "em" | "ec" | "anot" | "false" | "true"
|
|
66
66
|
|
|
@@ -131,7 +131,7 @@ def parse(equation, funclist=None):
|
|
|
131
131
|
if tree_node.name == "pass_through":
|
|
132
132
|
return fxchange(tree_node.children[0])
|
|
133
133
|
return TreeNode(
|
|
134
|
-
"f_" + tree_node.name if tree_node.name in tmp3 + ["limitpinf", "limit", "try", "ref", "sqrt","imply","forall","exist","exclude","union","intersection","len","index","angle","charge","sum2","electricfield","line","point","sum","transpose","equationrhs","equationlhs","equation","covariance","variance","expect","error","laplace","dot","curl","pdif","diverge","gradient","rad","ge","le","gt","lt","eqtri","linesegment","midpoint","mag","point1","point2","point3","line1","line2","line3","log10","arcsin","arccos","arctan","list","cosec","sec","cot","equiv","or","not","and","circumcenter","eq","sub","add","sin","cos","tan","mul", "cross", "wmul","integrate","dif","pow","div","log","abs"] else "d_" + tree_node.name,
|
|
134
|
+
"f_" + tree_node.name if tree_node.name in tmp3 + ["U", "limitpinf", "limit", "try", "ref", "sqrt","imply","forall","exist","exclude","union","intersection","len","index","angle","charge","sum2","electricfield","line","point","sum","transpose","equationrhs","equationlhs","equation","covariance","variance","expect","error","laplace","dot","curl","pdif","diverge","gradient","rad","ge","le","gt","lt","eqtri","linesegment","midpoint","mag","point1","point2","point3","line1","line2","line3","log10","arcsin","arccos","arctan","list","cosec","sec","cot","equiv","or","not","and","circumcenter","eq","sub","add","sin","cos","tan","mul", "cross", "wmul","integrate","dif","pow","div","log","abs"] else "d_" + tree_node.name,
|
|
135
135
|
[fxchange(child) for child in tree_node.children]
|
|
136
136
|
)
|
|
137
137
|
|
|
@@ -155,5 +155,4 @@ def parse(equation, funclist=None):
|
|
|
155
155
|
return tree_node
|
|
156
156
|
|
|
157
157
|
tree_node = rfx(tree_node)
|
|
158
|
-
tree_node = flatten_tree(tree_node)
|
|
159
158
|
return tree_node
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
from .expand import expand
|
|
2
|
+
from .ode import diffsolve, inversediff, order, groupe, epowersplit
|
|
3
|
+
from .base import *
|
|
4
|
+
from .simplify import simplify
|
|
5
|
+
from .diff import diff2
|
|
6
|
+
from .fraction import fraction
|
|
7
|
+
from .parser import parse
|
|
8
|
+
from .inverse import inverse
|
|
9
|
+
from .factor import factor
|
|
10
|
+
|
|
11
|
+
def capital2(eq):
|
|
12
|
+
if eq.name == "f_pdif" and eq.children[0].name != "f_pdif":
|
|
13
|
+
return eq.children[0]
|
|
14
|
+
for child in eq.children:
|
|
15
|
+
out = capital2(child)
|
|
16
|
+
if out is not None:
|
|
17
|
+
return out
|
|
18
|
+
return None
|
|
19
|
+
def subs2(eq, orde):
|
|
20
|
+
if eq.name == "f_pdif":
|
|
21
|
+
if orde == 1:
|
|
22
|
+
return eq.children[0].fx("dif")/eq.children[1].fx("dif")
|
|
23
|
+
else:
|
|
24
|
+
return subs2(TreeNode("f_dif", eq.children), orde)
|
|
25
|
+
return TreeNode(eq.name, [subs2(child, orde) for child in eq.children])
|
|
26
|
+
def capital(eq):
|
|
27
|
+
if eq.name[:2] == "f_" and eq.name != eq.name.lower():
|
|
28
|
+
return eq
|
|
29
|
+
for child in eq.children:
|
|
30
|
+
out = capital(child)
|
|
31
|
+
if out is not None:
|
|
32
|
+
return out
|
|
33
|
+
return None
|
|
34
|
+
def abs_const(eq):
|
|
35
|
+
if eq.name == "f_abs":
|
|
36
|
+
return tree_form("v_101")*eq.children[0]
|
|
37
|
+
return TreeNode(eq.name, [abs_const(child) for child in eq.children])
|
|
38
|
+
def want(eq):
|
|
39
|
+
if eq.name == "f_want":
|
|
40
|
+
|
|
41
|
+
eq2 = eq.children[0]
|
|
42
|
+
v = [tree_form(item) for item in vlist(eq.children[0])]
|
|
43
|
+
lst = {}
|
|
44
|
+
if eq.children[1].name == "f_and":
|
|
45
|
+
for item in eq.children[1].children:
|
|
46
|
+
item = abs_const(item)
|
|
47
|
+
item = groupe(item)
|
|
48
|
+
for item2 in v:
|
|
49
|
+
if contain(item, item2):
|
|
50
|
+
out = inverse(item.children[0], str_form(item2))
|
|
51
|
+
if out is not None:
|
|
52
|
+
lst[item2] = out
|
|
53
|
+
break
|
|
54
|
+
for key in lst.keys():
|
|
55
|
+
eq2 = replace(eq2, key, lst[key])
|
|
56
|
+
if len(lst.keys()) == len(v):
|
|
57
|
+
return fraction(groupe(simplify(eq2)))
|
|
58
|
+
return TreeNode(eq.name, [want(child) for child in eq.children])
|
|
59
|
+
def absorb2(eq):
|
|
60
|
+
if "v_103" in vlist(eq):
|
|
61
|
+
v = vlist(eq)
|
|
62
|
+
v.remove("v_103")
|
|
63
|
+
if set(v)<set(["v_101", "v_102"]):
|
|
64
|
+
return tree_form("v_103")
|
|
65
|
+
if ["v_101"] == vlist(eq):
|
|
66
|
+
return tree_form("v_101")
|
|
67
|
+
if ["v_102"] == vlist(eq):
|
|
68
|
+
return tree_form("v_102")
|
|
69
|
+
if ["v_103"] == vlist(eq):
|
|
70
|
+
return tree_form("v_103")
|
|
71
|
+
return TreeNode(eq.name, [absorb2(child) for child in eq.children])
|
|
72
|
+
def absorb(eq):
|
|
73
|
+
return dowhile(epowersplit(eq), absorb2)
|
|
74
|
+
def pde_sep(eq):
|
|
75
|
+
if eq.name == "f_eq":
|
|
76
|
+
eq = eq.children[0]
|
|
77
|
+
r2 = parse("U(x,y)")
|
|
78
|
+
eq = replace(eq, r2, parse("x").fx("X") * parse("y").fx("Y"))
|
|
79
|
+
|
|
80
|
+
eq = fraction(simplify(fraction(TreeNode("f_eq", [diff2(eq), tree_form("d_0")]))))
|
|
81
|
+
|
|
82
|
+
out = inversediff(eq.children[0], tree_form("d_0"))
|
|
83
|
+
|
|
84
|
+
if out is not None:
|
|
85
|
+
out = list(out.children[0].children)
|
|
86
|
+
if contain(out[0], tree_form("v_1")):
|
|
87
|
+
out = out[::-1]
|
|
88
|
+
out[0] = simplify(-out[0])
|
|
89
|
+
|
|
90
|
+
lst = []
|
|
91
|
+
for i in range(2):
|
|
92
|
+
|
|
93
|
+
out[i] = TreeNode("f_eq", [out[i], tree_form("v_103")])
|
|
94
|
+
out[i] = fraction(simplify(out[i]))
|
|
95
|
+
r = capital(out[i])
|
|
96
|
+
lst.append(r)
|
|
97
|
+
out[i] = replace(out[i], r, tree_form(f"v_{1-i}"))
|
|
98
|
+
out[i] = subs2(out[i], order(out[i]))
|
|
99
|
+
|
|
100
|
+
out[i] = diffsolve(out[i])
|
|
101
|
+
|
|
102
|
+
out[i] = replace(out[i], tree_form(f"v_{1-i}"), r)
|
|
103
|
+
out = TreeNode("f_eq", [r2, TreeNode("f_want", [product(lst), TreeNode("f_and", out)])])
|
|
104
|
+
return replace(replace(out, lst[0], parse("a")), lst[1], parse("b"))
|
|
105
|
+
return out
|
mathai-0.7.7/mathai/diff.py
DELETED
|
@@ -1,74 +0,0 @@
|
|
|
1
|
-
from .simplify import simplify
|
|
2
|
-
from .base import *
|
|
3
|
-
from .trig import trig0
|
|
4
|
-
def diff(equation, var="v_0"):
|
|
5
|
-
def diffeq(eq):
|
|
6
|
-
eq = simplify(eq)
|
|
7
|
-
if "v_" not in str_form(eq):
|
|
8
|
-
return tree_form("d_0")
|
|
9
|
-
if eq.name == "f_add":
|
|
10
|
-
add = tree_form("d_0")
|
|
11
|
-
for child in eq.children:
|
|
12
|
-
add += diffeq(child)
|
|
13
|
-
return add
|
|
14
|
-
elif eq.name == "f_abs":
|
|
15
|
-
return diffeq(eq.children[0])*eq.children[0]/eq
|
|
16
|
-
elif eq.name == "f_pow" and eq.children[0].name == "s_e":
|
|
17
|
-
return diffeq(eq.children[1])*eq
|
|
18
|
-
elif eq.name == "f_tan":
|
|
19
|
-
return diffeq(eq.children[0])/(eq.children[0].fx("cos")*eq.children[0].fx("cos"))
|
|
20
|
-
elif eq.name == "f_log":
|
|
21
|
-
return diffeq(eq.children[0])*(tree_form("d_1")/eq.children[0])
|
|
22
|
-
elif eq.name == "f_arcsin":
|
|
23
|
-
return diffeq(eq.children[0])/(tree_form("d_1")-eq.children[0]*eq.children[0])**(tree_form("d_2")**-1)
|
|
24
|
-
elif eq.name == "f_arccos":
|
|
25
|
-
return tree_form("d_-1")*diffeq(eq.children[0])/(tree_form("d_1")-eq.children[0]*eq.children[0])**(tree_form("d_2")**-1)
|
|
26
|
-
elif eq.name == "f_arctan":
|
|
27
|
-
return diffeq(eq.children[0])/(tree_form("d_1")+eq.children[0]*eq.children[0])
|
|
28
|
-
elif eq.name == "f_pow" and "v_" in str_form(eq.children[1]):
|
|
29
|
-
a, b = eq.children
|
|
30
|
-
return a**b * ((b/a) * diffeq(a) + a.fx("log") * diffeq(b))
|
|
31
|
-
elif eq.name == "f_mul":
|
|
32
|
-
add = tree_form("d_0")
|
|
33
|
-
for i in range(len(eq.children)):
|
|
34
|
-
tmp = eq.children.pop(i)
|
|
35
|
-
if len(eq.children)==1:
|
|
36
|
-
eq2 = eq.children[0]
|
|
37
|
-
else:
|
|
38
|
-
eq2 = eq
|
|
39
|
-
add += diffeq(tmp)*eq2
|
|
40
|
-
eq.children.insert(i, tmp)
|
|
41
|
-
return add
|
|
42
|
-
elif eq.name == "f_sin":
|
|
43
|
-
eq.name = "f_cos"
|
|
44
|
-
return diffeq(eq.children[0])*eq
|
|
45
|
-
elif eq.name == "f_cos":
|
|
46
|
-
eq.name = "f_sin"
|
|
47
|
-
return tree_form("d_-1")*diffeq(eq.children[0])*eq
|
|
48
|
-
elif eq.name[:2] == "v_":
|
|
49
|
-
return TreeNode("f_dif", [eq])
|
|
50
|
-
elif eq.name == "f_pow" and "v_" not in str_form(eq.children[1]):
|
|
51
|
-
base, power = eq.children
|
|
52
|
-
dbase = diffeq(base)
|
|
53
|
-
b1 = power - tree_form("d_1")
|
|
54
|
-
bab1 = TreeNode("f_pow", [base, b1])
|
|
55
|
-
return power * bab1 * dbase
|
|
56
|
-
return TreeNode("f_dif", [eq, tree_form(var)])
|
|
57
|
-
def helper(equation, var="v_0"):
|
|
58
|
-
if equation.name == "f_dif":
|
|
59
|
-
if equation.children[0].name == var:
|
|
60
|
-
return tree_form("d_1")
|
|
61
|
-
if var not in str_form(equation.children[0]):
|
|
62
|
-
return tree_form("d_0")
|
|
63
|
-
else:
|
|
64
|
-
return equation
|
|
65
|
-
return TreeNode(equation.name, [helper(child, var) for child in equation.children])
|
|
66
|
-
def calc(eq):
|
|
67
|
-
if eq.name == "f_dif":
|
|
68
|
-
return diffeq(trig0(eq.children[0]))
|
|
69
|
-
return TreeNode(eq.name, [calc(child) for child in eq.children])
|
|
70
|
-
if var is None:
|
|
71
|
-
return simplify(calc(equation))
|
|
72
|
-
equation = diffeq(trig0(equation))
|
|
73
|
-
equation = helper(equation, var)
|
|
74
|
-
return simplify(equation)
|
mathai-0.7.7/mathai/ode.py
DELETED
|
@@ -1,189 +0,0 @@
|
|
|
1
|
-
from collections import Counter
|
|
2
|
-
from .diff import diff
|
|
3
|
-
from .factor import factor
|
|
4
|
-
from .expand import expand
|
|
5
|
-
from .base import *
|
|
6
|
-
from .fraction import fraction
|
|
7
|
-
from .simplify import simplify
|
|
8
|
-
import copy
|
|
9
|
-
|
|
10
|
-
def inversediff(lhs, rhs):
|
|
11
|
-
count = 5
|
|
12
|
-
while contain(rhs, tree_form("v_1")) or contain(lhs, tree_form("v_0")):
|
|
13
|
-
success = False
|
|
14
|
-
if rhs.name == "f_add":
|
|
15
|
-
for i in range(len(rhs.children)-1,-1,-1):
|
|
16
|
-
if not contain(rhs.children[i], tree_form("v_0")) or str_form(tree_form("v_1").fx("dif")) in [str_form(x) for x in factor_generation(rhs.children[i])]:
|
|
17
|
-
if contain(rhs.children[i], tree_form("v_0")) or contain(rhs.children[i], tree_form("v_1")):
|
|
18
|
-
success = True
|
|
19
|
-
lhs = lhs - rhs.children[i]
|
|
20
|
-
rhs.children.pop(i)
|
|
21
|
-
elif rhs.name == "f_mul":
|
|
22
|
-
for i in range(len(rhs.children)-1,-1,-1):
|
|
23
|
-
if not contain(rhs.children[i], tree_form("v_0")):
|
|
24
|
-
if contain(rhs.children[i], tree_form("v_0")) or contain(rhs.children[i], tree_form("v_1")):
|
|
25
|
-
success = True
|
|
26
|
-
lhs = lhs / rhs.children[i]
|
|
27
|
-
rhs.children.pop(i)
|
|
28
|
-
if len(rhs.children) == 1:
|
|
29
|
-
rhs = rhs.children[0]
|
|
30
|
-
rhs, lhs = copy.deepcopy([simplify(lhs), simplify(rhs)])
|
|
31
|
-
if rhs.name == "f_add":
|
|
32
|
-
for i in range(len(rhs.children)-1,-1,-1):
|
|
33
|
-
if not contain(rhs.children[i], tree_form("v_1")) or str_form(tree_form("v_0").fx("dif")) in [str_form(x) for x in factor_generation(rhs.children[i])]:
|
|
34
|
-
if contain(rhs.children[i], tree_form("v_0")) or contain(rhs.children[i], tree_form("v_1")):
|
|
35
|
-
success = True
|
|
36
|
-
lhs = lhs - rhs.children[i]
|
|
37
|
-
rhs.children.pop(i)
|
|
38
|
-
elif rhs.name == "f_mul":
|
|
39
|
-
for i in range(len(rhs.children)-1,-1,-1):
|
|
40
|
-
if not contain(rhs.children[i], tree_form("v_1")):
|
|
41
|
-
if contain(rhs.children[i], tree_form("v_0")) or contain(rhs.children[i], tree_form("v_1")):
|
|
42
|
-
success = True
|
|
43
|
-
lhs = lhs / rhs.children[i]
|
|
44
|
-
rhs.children.pop(i)
|
|
45
|
-
rhs, lhs = copy.deepcopy([simplify(lhs), simplify(rhs)])
|
|
46
|
-
if not success:
|
|
47
|
-
lhs, rhs = factor(lhs),factor(rhs)
|
|
48
|
-
count -= 1
|
|
49
|
-
if count == 0:
|
|
50
|
-
return simplify(e0(lhs-rhs))
|
|
51
|
-
return simplify(e0(lhs-rhs))
|
|
52
|
-
|
|
53
|
-
def allocvar():
|
|
54
|
-
return tree_form("v_101")
|
|
55
|
-
|
|
56
|
-
def epowersplit(eq):
|
|
57
|
-
if eq.name == "f_pow" and eq.children[1].name == "f_add":
|
|
58
|
-
return product([eq.children[0]**child for child in eq.children[1].children])
|
|
59
|
-
return TreeNode(eq.name, [epowersplit(child) for child in eq.children])
|
|
60
|
-
def esolve(s):
|
|
61
|
-
if s.name == "f_add" and "f_log" in str_form(s):
|
|
62
|
-
return product([tree_form("s_e")**child for child in s.children]) - tree_form("d_1")
|
|
63
|
-
return TreeNode(s.name, [esolve(child) for child in s.children])
|
|
64
|
-
def diffsolve_sep2(eq):
|
|
65
|
-
global tab
|
|
66
|
-
|
|
67
|
-
s = []
|
|
68
|
-
eq = simplify(expand(eq))
|
|
69
|
-
eq = e1(eq)
|
|
70
|
-
|
|
71
|
-
def vlor1(eq):
|
|
72
|
-
if contain(eq, tree_form("v_0")) and not contain(eq, tree_form("v_1")):
|
|
73
|
-
return True
|
|
74
|
-
if contain(eq, tree_form("v_1")) and not contain(eq, tree_form("v_0")):
|
|
75
|
-
return True
|
|
76
|
-
return False
|
|
77
|
-
if eq.name == "f_add" and all(vlor1(child) and [str_form(x) for x in factor_generation(copy.deepcopy(child))].count(str_form(tree_form(vlist(child)[0]).fx("dif")))==1 for child in eq.children):
|
|
78
|
-
for child in eq.children:
|
|
79
|
-
v = vlist(child)[0]
|
|
80
|
-
v2 = tree_form(v).fx("dif")
|
|
81
|
-
child = replace(child, v2, tree_form("d_1"))
|
|
82
|
-
child = simplify(child)
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
tmp6 = TreeNode("f_integrate", [child, tree_form(v)])
|
|
86
|
-
s.append(tmp6)
|
|
87
|
-
|
|
88
|
-
if s[-1] is None:
|
|
89
|
-
return None
|
|
90
|
-
s.append(allocvar())
|
|
91
|
-
else:
|
|
92
|
-
return None
|
|
93
|
-
s = summation(s)
|
|
94
|
-
s = simplify(e0(s))
|
|
95
|
-
|
|
96
|
-
return groupe(s)
|
|
97
|
-
def e0(eq):
|
|
98
|
-
return TreeNode("f_eq", [eq, tree_form("d_0")])
|
|
99
|
-
def e1(eq):
|
|
100
|
-
if eq.name == "f_eq":
|
|
101
|
-
eq = eq.children[0]
|
|
102
|
-
return eq
|
|
103
|
-
def groupe(eq):
|
|
104
|
-
eq = esolve(eq)
|
|
105
|
-
eq = simplify(eq)
|
|
106
|
-
eq = fraction(eq)
|
|
107
|
-
eq = simplify(eq)
|
|
108
|
-
eq = epowersplit(eq)
|
|
109
|
-
return eq
|
|
110
|
-
|
|
111
|
-
def diffsolve_sep(eq):
|
|
112
|
-
eq = epowersplit(eq)
|
|
113
|
-
|
|
114
|
-
eq = inversediff(tree_form("d_0"), eq.children[0].copy_tree())
|
|
115
|
-
return eq
|
|
116
|
-
|
|
117
|
-
def diffsolve(eq):
|
|
118
|
-
orig = eq.copy_tree()
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
eq = diffsolve_sep2(diffsolve_sep(eq))
|
|
122
|
-
if eq is None:
|
|
123
|
-
for i in range(2):
|
|
124
|
-
a = tree_form(f"v_{i}")
|
|
125
|
-
b = tree_form(f"v_{1-i}")
|
|
126
|
-
c = tree_form("v_2")
|
|
127
|
-
eq2 = replace(orig, b,b*a)
|
|
128
|
-
eq2 = expand(simplify(fraction(simplify(diff(eq2, None)))))
|
|
129
|
-
eq2 = diffsolve_sep(eq2)
|
|
130
|
-
eq2 = diffsolve_sep2(eq2)
|
|
131
|
-
if eq2 is not None:
|
|
132
|
-
return e0(TreeNode("f_subs", [replace(eq2.children[0],b,c), c,b/a]).fx("try"))
|
|
133
|
-
eq = orig
|
|
134
|
-
|
|
135
|
-
eq = fraction(eq)
|
|
136
|
-
eq = simplify(eq)
|
|
137
|
-
for i in range(2):
|
|
138
|
-
out = linear_dif(eq, tree_form(f"v_{i}"), tree_form(f"v_{1-i}"))
|
|
139
|
-
if out is not None:
|
|
140
|
-
return out
|
|
141
|
-
return eq
|
|
142
|
-
def clist(x):
|
|
143
|
-
return list(x.elements())
|
|
144
|
-
def collect_term(eq, term_lst):
|
|
145
|
-
|
|
146
|
-
lst = None
|
|
147
|
-
if eq.name == "f_add":
|
|
148
|
-
lst = eq.children
|
|
149
|
-
else:
|
|
150
|
-
lst = [eq]
|
|
151
|
-
|
|
152
|
-
other = []
|
|
153
|
-
dic = {}
|
|
154
|
-
term_lst = sorted(term_lst, key=lambda x: -len(factor_generation(x)))
|
|
155
|
-
for item2 in lst:
|
|
156
|
-
done = True
|
|
157
|
-
tmp2 = Counter(factor_generation(item2))
|
|
158
|
-
for index, item in enumerate(term_lst):
|
|
159
|
-
tmp = Counter(factor_generation(item))
|
|
160
|
-
|
|
161
|
-
if (tmp2&tmp) == tmp and clist((tmp2 - tmp)&tmp)==[]:
|
|
162
|
-
if item in dic.keys():
|
|
163
|
-
dic[item] += product(clist(tmp2-tmp))
|
|
164
|
-
else:
|
|
165
|
-
dic[item] = product(clist(tmp2-tmp))
|
|
166
|
-
done = False
|
|
167
|
-
break
|
|
168
|
-
if done:
|
|
169
|
-
other.append(item2)
|
|
170
|
-
other = summation(other)
|
|
171
|
-
|
|
172
|
-
for key in dic.keys():
|
|
173
|
-
dic[key] = simplify(dic[key])
|
|
174
|
-
return [dic, simplify(other)]
|
|
175
|
-
def linear_dif(eq, a, b):
|
|
176
|
-
eq = simplify(eq)
|
|
177
|
-
out = collect_term(eq.children[0], [b.fx("dif"), b*a.fx("dif"), a.fx("dif")])
|
|
178
|
-
|
|
179
|
-
if out[1] == tree_form("d_0"):
|
|
180
|
-
tmp = out[0][b.fx("dif")]
|
|
181
|
-
if tmp != tree_form("d_0"):
|
|
182
|
-
|
|
183
|
-
for key in out[0].keys():
|
|
184
|
-
out[0][key] = simplify(out[0][key]/tmp)
|
|
185
|
-
p, q = out[0][b*a.fx("dif")], -out[0][a.fx("dif")]
|
|
186
|
-
|
|
187
|
-
f = tree_form("s_e") ** TreeNode("f_integrate", [p, a])
|
|
188
|
-
return simplify(TreeNode("f_eq", [b*f, TreeNode("f_integrate", [q*f, a])+allocvar()]))
|
|
189
|
-
return None
|
mathai-0.7.7/mathai/pde.py
DELETED
|
@@ -1,139 +0,0 @@
|
|
|
1
|
-
from .ode import diffsolve
|
|
2
|
-
from .base import *
|
|
3
|
-
from .simplify import simplify
|
|
4
|
-
from .diff import diff
|
|
5
|
-
from .fraction import fraction
|
|
6
|
-
from .parser import parse
|
|
7
|
-
from .inverse import inverse
|
|
8
|
-
def capital2(eq):
|
|
9
|
-
if eq.name == "f_pdif":
|
|
10
|
-
return eq.children[0]
|
|
11
|
-
for child in eq.children:
|
|
12
|
-
out = capital2(child)
|
|
13
|
-
if out is not None:
|
|
14
|
-
return out
|
|
15
|
-
return None
|
|
16
|
-
def subs(eq, r2):
|
|
17
|
-
if eq.name == "f_dif":
|
|
18
|
-
return TreeNode("f_pdif", eq.children)
|
|
19
|
-
if eq == r2:
|
|
20
|
-
return parse("x").fx("X") * parse("y").fx("Y")
|
|
21
|
-
if eq.name == "f_pdif":
|
|
22
|
-
return subs(diff(subs(eq.children[0], r2), str_form(eq.children[1])), r2)
|
|
23
|
-
return TreeNode(eq.name, [subs(child, r2) for child in eq.children])
|
|
24
|
-
def inverse_pde(lhs, rhs, depth=3):
|
|
25
|
-
if depth < 0:
|
|
26
|
-
return None
|
|
27
|
-
|
|
28
|
-
lhs = simplify(lhs.copy_tree())
|
|
29
|
-
rhs = simplify(rhs.copy_tree())
|
|
30
|
-
|
|
31
|
-
# separation check: lhs has no y, rhs has no x
|
|
32
|
-
lhs_str = str_form(lhs)
|
|
33
|
-
rhs_str = str_form(rhs)
|
|
34
|
-
|
|
35
|
-
if "v_1" not in lhs_str and "v_0" not in rhs_str:
|
|
36
|
-
return [lhs, rhs]
|
|
37
|
-
|
|
38
|
-
sides = [lhs, rhs]
|
|
39
|
-
|
|
40
|
-
for side in range(2):
|
|
41
|
-
eq = sides[side]
|
|
42
|
-
|
|
43
|
-
if eq.name not in ("f_add", "f_mul"):
|
|
44
|
-
continue
|
|
45
|
-
|
|
46
|
-
# iterate over a COPY — never mutate while iterating
|
|
47
|
-
for i, child in enumerate(eq.children.copy()):
|
|
48
|
-
# rebuild remaining expression safely
|
|
49
|
-
rest_children = [
|
|
50
|
-
c.copy_tree()
|
|
51
|
-
for j, c in enumerate(eq.children)
|
|
52
|
-
if j != i
|
|
53
|
-
]
|
|
54
|
-
|
|
55
|
-
if not rest_children:
|
|
56
|
-
continue
|
|
57
|
-
|
|
58
|
-
if len(rest_children) == 1:
|
|
59
|
-
rest = rest_children[0]
|
|
60
|
-
else:
|
|
61
|
-
rest = TreeNode(eq.name, rest_children)
|
|
62
|
-
|
|
63
|
-
other = sides[1 - side].copy_tree()
|
|
64
|
-
|
|
65
|
-
# move term across
|
|
66
|
-
if eq.name == "f_add":
|
|
67
|
-
moved = TreeNode("f_add", [other, -child.copy_tree()])
|
|
68
|
-
else: # f_mul
|
|
69
|
-
moved = TreeNode("f_mul", [other, TreeNode("f_pow", [child.copy_tree(), tree_form("d_-1")])])
|
|
70
|
-
|
|
71
|
-
moved = simplify(moved)
|
|
72
|
-
rest = simplify(rest)
|
|
73
|
-
|
|
74
|
-
if side == 0:
|
|
75
|
-
out = inverse_pde(rest, moved, depth - 1)
|
|
76
|
-
else:
|
|
77
|
-
out = inverse_pde(moved, rest, depth - 1)
|
|
78
|
-
|
|
79
|
-
if out is not None:
|
|
80
|
-
return out
|
|
81
|
-
|
|
82
|
-
return None
|
|
83
|
-
def subs2(eq):
|
|
84
|
-
if eq.name == "f_pdif":
|
|
85
|
-
return eq.children[0].fx("dif")/eq.children[1].fx("dif")
|
|
86
|
-
return TreeNode(eq.name, [subs2(child) for child in eq.children])
|
|
87
|
-
def capital(eq):
|
|
88
|
-
if eq.name[:2] == "f_" and eq.name != eq.name.lower():
|
|
89
|
-
return eq
|
|
90
|
-
for child in eq.children:
|
|
91
|
-
out = capital(child)
|
|
92
|
-
if out is not None:
|
|
93
|
-
return out
|
|
94
|
-
return None
|
|
95
|
-
def abs_const(eq):
|
|
96
|
-
if eq.name == "f_abs":
|
|
97
|
-
return tree_form("v_101")*eq.children[0]
|
|
98
|
-
return TreeNode(eq.name, [abs_const(child) for child in eq.children])
|
|
99
|
-
def want(eq):
|
|
100
|
-
if eq.name == "f_want":
|
|
101
|
-
eq2 = eq.children[0]
|
|
102
|
-
v = [tree_form(item) for item in vlist(eq.children[0])]
|
|
103
|
-
lst = {}
|
|
104
|
-
if eq.children[1].name == "f_and":
|
|
105
|
-
for item in eq.children[1].children:
|
|
106
|
-
item = abs_const(item)
|
|
107
|
-
for item2 in v:
|
|
108
|
-
if contain(item, item2):
|
|
109
|
-
out = inverse(item.children[0], str_form(item2))
|
|
110
|
-
if out is not None:
|
|
111
|
-
lst[item2] = out
|
|
112
|
-
break
|
|
113
|
-
for key in lst.keys():
|
|
114
|
-
eq2 = replace(eq2, key, lst[key])
|
|
115
|
-
if len(lst.keys()) == len(v):
|
|
116
|
-
return simplify(eq2)
|
|
117
|
-
return TreeNode(eq.name, [want(child) for child in eq.children])
|
|
118
|
-
def pde_sep(eq):
|
|
119
|
-
if eq.name == "f_eq":
|
|
120
|
-
eq = eq.children[0]
|
|
121
|
-
r2 = capital2(eq)
|
|
122
|
-
|
|
123
|
-
eq = simplify(fraction(subs(eq, r2)))
|
|
124
|
-
out = inverse_pde(eq,tree_form("d_0"))
|
|
125
|
-
if out is not None:
|
|
126
|
-
out = list(out)
|
|
127
|
-
lst = []
|
|
128
|
-
for i in range(2):
|
|
129
|
-
out[i] = subs2(out[i])
|
|
130
|
-
out[i] = TreeNode("f_eq", [out[i], tree_form("v_102")])
|
|
131
|
-
out[i] = fraction(simplify(out[i]))
|
|
132
|
-
r = capital(out[i])
|
|
133
|
-
lst.append(r)
|
|
134
|
-
out[i] = replace(out[i], r, tree_form(f"v_{1-i}"))
|
|
135
|
-
out[i] = diffsolve(out[i])
|
|
136
|
-
out[i] = replace(out[i], tree_form(f"v_{1-i}"), r)
|
|
137
|
-
out = TreeNode("f_eq", [r2, TreeNode("f_want", [product(lst), TreeNode("f_and", out)])])
|
|
138
|
-
return replace(replace(out, lst[0], parse("a")), lst[1], parse("b"))
|
|
139
|
-
return out
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|