Can I use lambdify to evaluate a derived python function?

Yesterday I asked a question about differentiating a python function, and then when I found that none of the answers was satisfactory for my need for evaluation (in some variables) and then building a derivative, I was able to figure out my solution.

Previous code:

import sympy as sym
import math


def f(x,y):
    return x**2 + x*y**2


x, y = sym.symbols('x y')

def fprime(x,y):
    return sym.diff(f(x,y),x)

print(fprime(x,y)) #This works.

print(fprime(1,1)) 

New code:

import sympy as sym
import math


def f(x,y):
    return x**2 + x*y**2


x, y = sym.symbols('x y')

def fprime(x,y):
    return sym.diff(f(x,y),x)

print(fprime(x,y)) #This works.

DerivativeOfF = sym.lambdify((x,y),fprime(x,y),"numpy")

print(DerivativeOfF(1,1))

As you can see, I overcame the inability to evaluate the fprime derivative by creating a new DerivativeOfF function, which was the "lambdified" version of fprime. From there, I was able to evaluate DerivativeOfF, and also build it in one of the variables.

:, ? ? ? lambdify, ( Python). , Python fprime Sympy DerivativeOfF - . , , , ( ), .

+4
3

, . Python numpy, sympy ( , macsyma).

numpy ipython:

In [1]: def f(x,y):
   ...:     return x**2 + x*y**2
   ...: 
In [2]: f(1,3)
Out[2]: 10
In [3]: f(np.arange(1,4), np.arange(10,13))
Out[3]: array([101, 246, 441])

f - python; , , , *, ** +. . + * (, ), **.

In [4]: import sympy as sym
In [5]: x, y = sym.symbols('x y')
In [6]: type(x)
Out[6]: sympy.core.symbol.Symbol
In [7]: x+y
Out[7]: x + y
In [8]: type(_)
Out[8]: sympy.core.add.Add

symbols . + .. .

In [9]: fsym = f(x,y)
In [10]: type(fsym)
Out[10]: sympy.core.add.Add
In [11]: print(fsym)
x**2 + x*y**2

f sym. .

In [12]: f(x,0)
Out[12]: x**2
In [13]: f(1,x)
Out[13]: x**2 + 1
In [14]: f(np.arange(3), x)
Out[14]: array([0, x**2 + 1, 2*x**2 + 4], dtype=object)

Add sym.diff, Add

In [15]: fprime = sym.diff(fsym,x)
In [16]: fprime
Out[16]: 2*x + y**2

fsym, fprime . Python. fsym(1,2) .

fsym.subs x / y , :

In [19]: fsym.subs(x,1)
Out[19]: y**2 + 1
In [20]: fsym.subs(y,2*x)
Out[20]: 4*x**3 + x**2
In [21]: fsym.subs([(x,1),(y,2)])
Out[21]: 5
In [22]: fprime.subs([(x,1),(y,2)])
Out[22]: 6

lambdify - sympy, sympy Python, numpy compatible`.

In [24]: fl = sym.lambdify((x,y), fsym, "numpy")
In [25]: fl
Out[25]: <function numpy.<lambda>>
In [26]: fl(1,2)
Out[26]: 5
In [27]: fl(np.arange(1,4), np.arange(10,13))   # cf with f(same) above
Out[27]: array([101, 246, 441])

fl f. , , help/doc.

lambdify fprime , :

In [28]: fpl = sym.lambdify((x,y), fprime, "numpy")
In [29]: fpl(1,2)
Out[29]: 6
In [30]: fpl(np.arange(1,4), np.arange(10,13))
Out[30]: array([102, 125, 150])

python/numpy sympy . () . , math.sin, numpy.sin sym.sin.

sym.diff.

In [35]: fsym
Out[35]: x**2 + x*y**2
In [36]: fprime
Out[36]: 2*x + y**2

sym.lambdify - Python.

, sym sin/cos:

In [53]: def f1(x,y):
    ...:     return sym.sin(x) + x*sym.sin(y)
    ...: 
In [54]: f1(x,y)
Out[54]: x*sin(y) + sin(x)
In [55]: f1(1,2)
Out[55]: sin(1) + sin(2)
In [56]: f1(1, np.arange(3)
...
SympifyError: Sympify of expression 'could not parse '[0 1 2]'' failed, because of exception being raised:
SyntaxError: invalid syntax (<string>, line 1)

, , sym.sin(<array>) ; np.sin(...), .

, :

In [57]: sym.diff(f1(x,y),x)
Out[57]: sin(y) + cos(x)
In [58]: sym.diff(f1(x,y),y)
Out[58]: x*cos(y)
In [59]: sym.diff(sym.diff(f1(x,y),x),y)
Out[59]: cos(y)

. subs lambdify.

In [60]: f2 = sym.lambdify((x,y),f1(x,y),"numpy")
In [61]: f2
Out[61]: <function numpy.<lambda>>
In [62]: f2(1, np.arange(3))
Out[62]: array([ 0.84147098,  1.68294197,  1.75076841])

f2 , f1. sympy np.sin sym.sin.

, f2 , numpy :

In [63]: f2(1,y)
...
/usr/local/lib/python3.5/dist-packages/numpy/__init__.py in <lambda>(_Dummy_30, _Dummy_31)
AttributeError: 'Symbol' object has no attribute 'sin'

In [66]: sym.diff(f2(x,y),x)
 ....
AttributeError: 'Symbol' object has no attribute 'sin'
+2

sym.lambdify python,

def DerivativeOff(x,y):
    return 2*x + y**2

numpy, , python. , DerivativeOff, . DeravativeOff(x,y) .

, , python . :

def f2(x,y):
    return sym.sin(x)*y

def fprime2(x,y):
    return sym.diff(f2(x,y),x)

DerivativeOff2 = sym.lambdify((x,y), fprime2(x,y), "numpy")

print(DerivativeOff2(1,2)) #will return a number

print(DerivativeOff2(x,y)) #will give an error

lambdify sin . numpy ( "numpy" ). , DerivatifeOff2

def DerivativeOff2(x,y):
    return numpy.cos(x)*y

, , numpy ...

, , sympy ( matplotlib): http://docs.sympy.org/latest/modules/plotting.html

3d- .

EDIT: :

import sympy as sym
def f(x,y):
    return sym.sin(x) + x*sym.sin(y)
def fprime(x,y):
    return sym.diff(f(x,y),y)
x, y = sym.symbols('x y')
print(fprime(1,y)) #works perfectly fine
print(fprime(x,1)) #does not work because it would mean to derive with respect to 1
print(fprime(x,y).subs(y,1)) #works, derives with respect to y, then substitutes 1 for y
+1

lambdify , SymPy , . (), lambdify ( , ).

x, y = sym.symbols('x y')

def fprime(x,y):
    return sym.diff(f(x,y),x)

, , "def fprime (x, y)", x y, . , sym.diff(f(x,y),x) Symbol, symbols('x y'), , fprime. , , , . f(x, y).

. .

x, y = sym.symbols('x y')
expr = x**2 + x*y**2
fprime = diff(expr, x)

, fprime , subs.

fprime.subs({x: 1, y: 1})

If at this point you want to create a quick function that uses NumPy to evaluate an expression for a number or an array of numbers, here you should use lambdify.

f = lambdify((x, y), expr, 'numpy')
import numpy as np
f(np.array([1]), np.array([2]))

(also, as a rule, if you are an lambdifyexpression with 'numpy', you must pass in lumpdified arrays to NumPy arrays)

0
source

Source: https://habr.com/ru/post/1678259/


All Articles