легко понять, что
from sympy import *
x = symbols('x', real=True)
y = sin(x)
dy = y.diff(x)
ddy = y.diff(x, 2)
print(y.subs(x, pi/2), dy.subs(x, pi/2), ddy.subs(x, pi/2), )
1 0 -1
теперь, если выражение y не определено заранее, но должно быть введено пользователем, например
y = input('please input expression about x: ')
y = sympify(y)
dy = y.diff(x)
ddy = y.diff(x, 2)
но если пользователь снова вводит sin(x)
print(y.subs(x, pi/2), dy.subs(x, pi/2), ddy.subs(x, pi/2), )
говорит
sin(x) 0 0
а также
print(y.subs('x', pi/2), dy.subs('x', pi/2), ddy.subs('x', pi/2), )
говорит
1 0 0
поэтому sympify не знает x
как символ, как это делает sympy.sin(x)
. Итак, как мы можем это исправить? Спасибо
Поэтому есть параметр locals
в sympify
:
y = sympify(y, locals={'x': x})
Это не было бы необходимо, если бы ваш x
не имел предположения real=True
. Символы считаются одинаковыми, если они имеют одинаковые атрибуты: имя и предположения. Символ, полученный из строки sin(x)
не имеет для него предположений, таких как вещественные. Таким образом, имя соответствует вашему x
но предположения нет.
Другой подход заключается в том, чтобы не ограничивать пользователя именем переменной x
; просто используйте любой символ, который они использовали.
y = sympify(y)
x = next(iter(y.free_symbols)) # get the first (and hopefully only) symbol in the formula
dy = y.diff(x)
# and so on
dy = y.diff('x')
тогдаdy.subs('x', pi/2)
работает. Но если я хочу предварительно определить некоторые функции в моем источнике, я все же предпочитаю последовательное и краткое выражение Python