I’m trying to create a function in Python 2.7 that accepts a function handle and the number of variables in the function as the input and returns a new function that calculates the gradient of the input function. This is what I have so far.
import sympy as sym
import numpy as np
def getSymbolicGradient(func,numVars):
# Initialize Some Variables
g = numVars * [0]
# Create All the Symbolic Variables
x = sym.symarray('x',numVars)
# Calculate the Gradients
for i in range(numVars):
g[i] = sym.diff(func(x),x[i])
gradFunc = sym.lambdify(x, g, modules="numpy")
return gradFunc
Say I use gradFunc
with the following code:
def myVecFunc(x):
return 2*x[0]**2 + 4*x[1] + 2
gradFunc = getSymbolicGradient(func=myVecFunc, numVars=2)
If I call it using two separate arguments it works, such as the following:
print( gradFunc(1,2) )
However, if I call it using a single argument (say a Numpy array),
print( gradFunc(np.array([1,2])) )
I get the following error:
TypeError: () takes exactly 2 arguments (1 given)
How can I get lambdify
to accept the input arguments as a single array inside of individual values? Are there better (built-in) Sympy methods for generating a symbolic expression for a gradient of a function that accepts arrays as inputs?
I'm not too familiar with numpy, but generally in Python you can use the *
operator to unpack array values.
a = [2, 4, 6]
my_func(*a)
is logically equivalent to
a = 2
b = 4
c = 6
my_func(a, b, c)