mirror of
https://github.com/Sosokker/Calculator-for-Matrix-and-Algebra.git
synced 2025-12-18 12:44:05 +01:00
Fix some polynomial can plus,minus with int float and implement quadratic polynomial solver. Some error still exist. Fix and implement to_str function(array to text).
This commit is contained in:
parent
2e814ec9cc
commit
c143c0ca2f
@ -1,7 +1,9 @@
|
||||
from parser.parser import parse_poly
|
||||
from fraction import to_fraction
|
||||
from math import sqrt
|
||||
|
||||
class Polynomial:
|
||||
def __init__(self, poly):
|
||||
def __init__(self, poly, fracmode=False):
|
||||
if isinstance(poly, str):
|
||||
self.coeff = parse_poly(poly)
|
||||
self.degree = len(parse_poly(poly)) - 1
|
||||
@ -12,6 +14,13 @@ class Polynomial:
|
||||
self.string_form = self.to_str()
|
||||
else:
|
||||
raise ValueError
|
||||
self.fracmode = fracmode
|
||||
if fracmode:
|
||||
for c_index in range(len(self.coeff)):
|
||||
try:
|
||||
self.coeff[c_index] = to_fraction(self.coeff[c_index])
|
||||
except:
|
||||
raise ValueError("Can't turn all number into fraction.")
|
||||
|
||||
#[degree0, degree1, degree2]
|
||||
def __add__(self, other):
|
||||
@ -19,67 +28,194 @@ class Polynomial:
|
||||
>>> p1 = Polynomial([1, 1, 1, 1, 1])
|
||||
>>> p2 = Polynomial([1, 1, 1, 1, 1])
|
||||
>>> p3 = p1 + p2
|
||||
>>> p3
|
||||
2x^4+2x^3+2x^2+2x+2
|
||||
>>> str(p3)
|
||||
'2x^4+2x^3+2x^2+2x+2'
|
||||
"""
|
||||
if isinstance(other, Polynomial):
|
||||
large_index = max([self.degree, other.degree])
|
||||
temp = [0 for i in range(large_index)]
|
||||
result = Polynomial(temp)
|
||||
for degree_index in range(self.degree):
|
||||
self.coeff[degree_index] += other.coeff[degree_index]
|
||||
if isinstance(other, int) or isinstance(other, float):
|
||||
pass
|
||||
|
||||
result.coeff[degree_index] = self.coeff[degree_index] + other.coeff[degree_index]
|
||||
return result
|
||||
elif isinstance(other, (int, float)):
|
||||
result = Polynomial(self.coeff)
|
||||
result.coeff[0] += other
|
||||
return result
|
||||
|
||||
def __sub__(self, other):
|
||||
"""
|
||||
>>> p1 = Polynomial([1, 1, 1, 1, 1])
|
||||
>>> p2 = Polynomial([1, 1, 1, 1, 1])
|
||||
>>> p3 = p1 - p2
|
||||
>>> p3
|
||||
0
|
||||
>>> str(p3)
|
||||
'0'
|
||||
"""
|
||||
if isinstance(other, Polynomial):
|
||||
large_index = max([self.degree, other.degree])
|
||||
temp = [0 for i in range(large_index)]
|
||||
result = Polynomial(temp)
|
||||
for degree_index in range(self.degree):
|
||||
self.coeff[degree_index] -= other.coeff[degree_index]
|
||||
|
||||
result.coeff[degree_index] = self.coeff[degree_index] - other.coeff[degree_index]
|
||||
return result
|
||||
elif isinstance(other, (int, float)):
|
||||
result = Polynomial(self.coeff)
|
||||
result.coeff[0] -= other
|
||||
return result
|
||||
|
||||
def __mul__(self, other):
|
||||
"""
|
||||
>>> p1 = Polynomial([1, 1])
|
||||
>>> p2 = Polynomial([1, 1])
|
||||
>>> p3 = p1 * p2
|
||||
>>> str(p3)
|
||||
x^2+2x+1
|
||||
"""
|
||||
if isinstance(other, Polynomial):
|
||||
result = [0 for i in self.degree + other.degree]
|
||||
for self_index in range(self.degree):
|
||||
for other_index in range(other.degree):
|
||||
result[self_index+other_index] += self.coeff[self_index]*other.coeff[other_index]
|
||||
poly_result = Polynomial(result)
|
||||
return poly_result
|
||||
elif isinstance(other, int) or isinstance(other, float):
|
||||
result = [0 for i in self.degree + other.degree]
|
||||
for self_index in range(self.degree):
|
||||
result[self_index+other_index] += self.coeff[self_index]*other
|
||||
poly_result = Polynomial(result)
|
||||
return poly_result
|
||||
|
||||
def __pow__(self):
|
||||
pass
|
||||
def __pow__(self, other):
|
||||
"""
|
||||
>>> p1 = Polynomial([1, 1])
|
||||
>>> str(p1 ** 2)
|
||||
x^2+2x+1
|
||||
"""
|
||||
result = Polynomial([0])
|
||||
if isinstance(other, int) and other >= 0:
|
||||
if other == 0:
|
||||
return Polynomial([1])
|
||||
else:
|
||||
for i in range(other):
|
||||
result += self * self
|
||||
return result
|
||||
|
||||
def __truediv__(self):
|
||||
pass
|
||||
|
||||
def to_str(self):
|
||||
def to_str(self) -> str:
|
||||
"""
|
||||
convert coefficient list into string.
|
||||
>>> p1 = Polynomial([1, 1, 1, 1, 1])
|
||||
>>> p1.to_str()
|
||||
x^4+x^3+x^2+x+1
|
||||
'x^4+x^3+x^2+x+1'
|
||||
>>> p2 = Polynomial([-2, 4, 0, -1, 2])
|
||||
>>> p2.to_str()
|
||||
2x^4-x^3+4x-2
|
||||
'2x^4-x^3+4x-2'
|
||||
"""
|
||||
result = []
|
||||
for ind in range(len(self.coeff)):
|
||||
if self.coeff[ind]:
|
||||
if ind == 0:
|
||||
temp = ""
|
||||
elif ind == 1:
|
||||
temp = "x"
|
||||
else:
|
||||
temp = "x^"+str(ind)
|
||||
result.append(str(self.coeff[ind])+temp)
|
||||
# result = []
|
||||
# for ind in range(len(self.coeff)):
|
||||
# if self.coeff[ind]:
|
||||
# if ind == 0:
|
||||
# temp = ""
|
||||
# elif ind == 1:
|
||||
# temp = "x"
|
||||
# else:
|
||||
# temp = "x^"+str(ind)
|
||||
# result.append(str(self.coeff[ind])+temp)
|
||||
|
||||
if result:
|
||||
result.reverse()
|
||||
return " + ".join(result)
|
||||
else:
|
||||
return "0"
|
||||
# if result:
|
||||
# result.reverse()
|
||||
# return "+".join(result)
|
||||
# else:
|
||||
# return "0"
|
||||
|
||||
result = []
|
||||
i = len(self.coeff) - 1
|
||||
while i >= 0:
|
||||
if self.coeff[i] != 0:
|
||||
if self.coeff[i] < 0:
|
||||
result.append("-")
|
||||
|
||||
elif len(self.coeff) != 0:
|
||||
result.append("+")
|
||||
|
||||
elif self.coeff[i] == 0:
|
||||
i -= 1
|
||||
continue
|
||||
|
||||
if self.coeff[i] != 1 and self.coeff[i] != -1:
|
||||
result.append(str(abs(self.coeff[i])))
|
||||
|
||||
if (i == len(self.coeff) - 1):
|
||||
result.append(str(self.coeff[i]))
|
||||
|
||||
if (self.coeff[i] == 1) and (i != len(self.coeff) - 1):
|
||||
result.append(str(1))
|
||||
|
||||
if i == 1:
|
||||
result.append("x")
|
||||
|
||||
if i > 1:
|
||||
result.append("x^"+str(i))
|
||||
i -= 1
|
||||
|
||||
if result[0] == "+" or result[0] == "-":
|
||||
del result[0]
|
||||
result = "".join(result)
|
||||
|
||||
return result
|
||||
|
||||
def solve(self) -> tuple:
|
||||
degree = len(self.coeff) - 1
|
||||
if degree == 2:
|
||||
a, b, c = self.coeff[2], self.coeff[1], self.coeff[0]
|
||||
if a == 0:
|
||||
if b == 0:
|
||||
if c == 0:
|
||||
return (0, None)
|
||||
else:
|
||||
return (c, None)
|
||||
else:
|
||||
return (-c/b, None)
|
||||
else:
|
||||
root_term = b**2-4*a*c
|
||||
if root_term < 0:
|
||||
res1 = f"({-b}+{to_imag(sqrt(root_term))})/{2*a}"
|
||||
res2 = f"({-b}-{to_imag(sqrt(root_term))})/{2*a}"
|
||||
return (res1, res2)
|
||||
else:
|
||||
if root_term == 0:
|
||||
return (-b/(2*a), None)
|
||||
else:
|
||||
try:
|
||||
res1 = (-b-sqrt(root_term))/(2*a)
|
||||
res2 = (-b+sqrt(root_term))/(2*a)
|
||||
except TypeError:
|
||||
res1 = (-b-(root_term)**0.5)/(2*a)
|
||||
res2 = (-b+(root_term)**0.5)/(2*a)
|
||||
return (res1, res2)
|
||||
|
||||
def __str__(self) -> str:
|
||||
return self.string_form
|
||||
return self.string_form
|
||||
|
||||
def to_imag(num) -> str:
|
||||
"""
|
||||
>>> to_imag(-10)
|
||||
'10i'
|
||||
>>> to_imag(-10.12)
|
||||
'10.12i'
|
||||
"""
|
||||
num = abs(float(num))
|
||||
return f"{num}i"
|
||||
|
||||
# p1 = Polynomial("x^2+2x+1", fracmode=True)
|
||||
# p2 = Polynomial("x^2+2x+1", fracmode=False)
|
||||
|
||||
# print(p1.solve())
|
||||
|
||||
# if __name__ == "__main__":
|
||||
# import doctest
|
||||
# doctest.testmod()
|
||||
# Use the following line INSTEAD if you want to print all tests anyway.
|
||||
# doctest.testmod(verbose = True)
|
||||
Loading…
Reference in New Issue
Block a user