Я пытаюсь вычислить все возможные реальные значения X при определенном значении Y из полинома, заданного в порядке убывания коэффициентов, в Python 3.10. Я хочу, чтобы результирующие значения X были предоставлены мне в виде list.
Я пытался использовать функцию roots() библиотеки numpy, как показано в одном из ответов на этот пост, однако это не работает:
import numpy as np
import matplotlib.pyplot as plt
def main():
coeffs = np.array([1, 2, 2])
y = 1.5
polyDataX = np.linspace(-2, 0)
polyDataY = np.empty(shape = len(polyDataX), dtype = float)
for i in range(len(polyDataX)):
polyDataY[i] = coeffs[0] * pow(polyDataX[i], 2) + coeffs[1] * polyDataX[i] + coeffs[2]
coeffs[-1] -= y
x = np.roots(coeffs).tolist()
plt.axhline(y, color = "orange")
plt.plot(polyDataX, polyDataY, color = "blue")
plt.title("X = " + str(x))
plt.show()
plt.close()
plt.clf()
if (__name__ == "__main__"):
main()
В моем примере выше коэффициенты моего полинома хранятся в локальной переменной coeffs в порядке убывания. Затем я пытаюсь собрать все X-значения в Y-значении 0.5, хранящиеся в локальных переменных x и y соответственно. Затем я отображаю собранные значения X в качестве заголовка отображаемого графика.
Приведенный выше сценарий приводит к следующему графику:
Со значениями X, показанными как [-2.0, 0.0], вместо правильного:
Каков правильный способ получить все реальные значения X многочлена при определенном значении Y в Python?
Спасибо, что прочитали мой пост, любые рекомендации приветствуются.






Ваш код правильный, и вы правильно используете корневую функцию. Есть только небольшая проблема с типами данных.
Вы можете увидеть ошибку с помощью отладчика или напечатать coeff после coeffs[-1] -= y. В вашей строке coeffs = np.array([1, 2, 2]) numpy создаст массив с целочисленным типом, и поэтому ваше вычитание, которое должно привести к 0.5, на самом деле приводит к 0, поэтому ваши коэффициенты становятся [1, 2, 0]. Для них вычисляется правильный результат. Итак, нам нужно просто установить для dtype значение float:
import numpy as np
import matplotlib.pyplot as plt
def main():
coeffs = np.array([1, 2, 2], dtype=float) #<-----------
y = 1.5
polyDataX = np.linspace(-2, 0)
polyDataY = np.empty(shape = len(polyDataX), dtype = float)
for i in range(len(polyDataX)):
polyDataY[i] = coeffs[0] * pow(polyDataX[i], 2) + coeffs[1] * polyDataX[i] + coeffs[2]
coeffs[-1] -= y
x = np.roots(coeffs).tolist()
plt.axhline(y, color = "orange")
plt.plot(polyDataX, polyDataY, color = "blue")
plt.title("X = " + str(x))
plt.show()
plt.close()
plt.clf()
if __name__ == "__main__":
main()
Решение уравнения f(x) = y эквивалентно решению f(x) - y = 0, т. е. нахождению корней. Вот что происходит здесь, когда вы вычитаете y.
Значения в coeffs равны int32, а результат после coeffs[-1] -= y равен 0, а не 0,5.
Просто поменяй coeffs = np.array([1, 2, 2]) на coeffs = np.array([1., 2., 2.])
Вы должны использовать класс numpy.polynomial.Polynomial , который был добавлен в numpy v1.4 (дополнительная информация здесь). С помощью этого класса вы можете создать полиномиальный объект. Чтобы найти свое решение, вы можете вычесть y из объекта Polynomial, а затем вызвать метод roots. Еще одна приятная особенность заключается в том, что вы можете напрямую вызывать объект, который вы можете использовать для вычисления polyDataY.
Просто обратите внимание, что класс Polynomial ожидает, что коэффициенты будут заданы в обратном порядке от np.roots, то есть квадратное число x^2 + 2x + 2 должно иметь коэффициенты (2, 2, 1). Чтобы все соответствовало тому, что вы дали, я просто передаю наоборот coeffs.
import numpy as np
from numpy.polynomial import Polynomial
import matplotlib.pyplot as plt
plt.close("all")
coeffs = np.array([1, 2, 2])
poly = Polynomial(coeffs[::-1])
polyDataX = np.linspace(-2, 0)
polyDataY = poly(polyDataX)
y = 1.5
x = (poly - y).roots()
plt.axhline(y, color = "orange")
plt.plot(polyDataX, polyDataY, color = "blue")
plt.title("X = " + str(x))
plt.show()
Спасибо, что поделились этим решением, оно сработало. Просто из любопытства, что на самом деле делает строка
coeffs[-1] -= y? Сдвигает ли это весь многочлен, чтобы сделать так, чтобы0совпадало со значениемy, чтобы мы могли вычислить корни? Если да, то почему мы просто меняем коэффициенты?