Python scipy module derivate not working with input from user - python

When I tried to calculate a derivate from an user it gave me an error, that says that derivate does not take string inputs, but so how Ican achieve this
import scipy.misc import derivate
fx=input()
print(derivative(fx,1.0,dx=1e-8))

The first parameter is func, not str docs. If you want it as input you can use lambda and eval. The input need to be in x**3 + x**2 format
fx = input()
f = lambda x: eval(fx)
print(derivative(f, 1.0, dx=1e-8))

Use below code
from scipy.misc import derivative
def f(x):
return x**2 + x
print(derivative(f,1.0,dx=1e-6))
------------ Updated---------------------
Explanation: - With your code you have tried to pass a string to the function derivative which expects a function instead , here is the doc

Related

How to use exp() in integration function?

Here is a snippet of my code.
from scipy.integrate import quad
from numpy import exp, log, inf
def f(x):
return log(log(x))/(x*log(x**2))
val, err = quad(f, exp(), exp(2))
val
I know the code is structured correctly but I cannot format the exp() correctly. What am I doing wrong? The function should output 0.069324. Thanks ahead of time for the help!!!
Here is the answer from WolfRamAlpha:
numpy's exp is a function, not a number. You want
exp(1) = e
exp(2) = e**2
or maybe
import numpy as np
np.e
np.e**2
as your integration limits.
That said, I get
from numpy import exp, log
def f(x):
return log(log(x))/(x*log(x**2))
val, err = quad(f, exp(1), exp(2))
val
returning 0.12011325347955035
This is definitely the value of this integral. You can change variables to verify
val,err = quad(lambda x: log(x)/(2*x),1,2)
which gives the same result
Just replace exp() by exp(1) and you are good to go. By the way, once you have figured out the correct function, you can also use one liner lambda functions. Your code is perfectly fine. I thought of just sharing another possible way to implement the same thing.
f = lambda x: np.log(np.log(x))/(x*np.log(x**2))
val, err = quad(f, exp(1), 2*exp(1))

Getting mathematical function as user's input

I need to know how transfer string input into executable function.
For example - user write string 'x*Sin(x**2)' and then programm takes it as function, can calculate a value for given x, can plot derivation of this function etc. I've read that there is module called scitools.stringfunction, but as far as I know this module is not callable in python-3.
Any ideas how to make it?
For Python 2.X
f = lambda x: input() # the user inputs: x**2 + 1
y = f(3)
print y # outputs: 10
For Python 3.X
f = lambda x: eval(input())
y = f(5)
print y
Just make sure to import the required mathematical functions. And make sure the user inputs a valid Python arithmetic expression.
using sympy you could do something like this:
from sympy import var
from sympy import sympify
x = var('x') # the possible variable names must be known beforehand...
user_input = 'x * sin(x**2)'
expr = sympify(user_input)
res = expr.subs(x, 3.14)
print(res) # -1.322...
if you want to turn the user input into a function you can call you could to this:
from sympy.utilities.lambdify import lambdify
f = lambdify(x, expr)
# f(3.14) -> -1.322...
sympy can do sybolic calculations (including derivatives); if you want to make plots i strongly suggest matplotlib.
the advantage of using a math library opposed to eval is that you do not need to sanitize the user input (against malicious code).
(deleted this thanks to a comment from ejm).

Why does scipy.optimize.fmin_l_bfgs_b fail to print iteration details despite appropriate inputs?

Goal:
To view the value of the objective function at each iteration for scipy.optimize.fmin_l_bfgs_b.
Problem:
Giving the optional argument iprint=1 should cause output to be printed. However, doing so does not result in any output.
Other info:
I am using the Anaconda 4.3 distribution of Python 2.7 on a Windows 7 machine, Spyder IDE with IPython console.
Example Code:
import numpy as np
import scipy.optimize as opt
A = np.random.rand(20,40)
b = np.random.rand(20,)
x0 = np.ones((40,))
def objective_func(x,A,b):
objective = np.sum((A.dot(x)-b)**2) + np.sum(np.abs(x))
return objective
def gradient_func(x,A,b):
gradient = 2*A.T.dot(A.dot(x)-b) + 2*x/np.sqrt(x**2 + 10**(-8))
return gradient
x_bar = opt.fmin_l_bfgs_b(func=objective_func,
x0=x0,
fprime = gradient_func,
args=(A,b),
iprint=1)
One solution is to use a lambda function as the callback function. This allows one to pass A, b to the callback function in addition to x.

ValueError: need more than 3 values to unpack when using optimize.minimize

I'm pretty new to python and I got stuck on this:
I'd like to use scipy.optimize.minimize to maximize a function and I'm having some problem with the extra arguments of the function I defined.
I looked for a solution in tons of answered questions but I can't find anything that solves my problem.
I saw in Structure of inputs to scipy minimize function how to pass extra arguments that one wants to be constant in the minimization of the function and my code seems fine to me from this point of view.
This is my code:
import numpy as np
from scipy.stats import pearsonr
import scipy.optimize as optimize
def min_pears_function(a,exp):
(b,c,d,e)=a
return (1-(pearsonr(b + exp[0] * c + exp[1] * d + exp[2],e)[0]))
a = (log_x,log_y,log_t,log_z) # where log_x, log_y, log_t and log_z are numpy arrays with same length
guess_PF=[0.6,2.0,0.2]
res = optimize.minimize(min_pears_function, guess_PF, args=(a,), options={'xtol': 1e-8, 'disp': True})
When running the code I get the following error:
ValueError: need more than 3 values to unpack
But I can't see what needed argument I'm missing. The function seems to work fine, so I guess the problem is in optimize.minimize call?
Your error occurs here:
def min_pears_function(a,exp):
# XXX: This is your error line
(b,c,d,e)=a
return (1-(pearsonr(b + exp[0] * c + exp[1] * d + exp[2],e)[0]))
This is because:
the initial value you pass to optimize.minimize is guessPF which has just three values ([0.6,2.0,0.2]).
this initial value is passed to min_pears_function as the variable a.
Did you mean for it to be passed as exp? Is it exp you wish to solve for? In that case, redefine the signature as:
def min_pears_function(exp, a):
...

How to take a function as an argument? (Python)

I'm writing a program to calculate the volume of a solid of rotation. The first step of this is to calculate an integral. I'm using scipy.integrate for this, but I can't figure out the best way to have a equation (like x=x**2 input at the command line. I was originally planning on adding an argument 'with respect to: x|y' and then taking the function as a lambda. Unfortunately, argparse won't take lambda as an argument type, and trying to use a string to construct a lambda (f = lambda x: args.equation) just returns a string (understandably really).
Here's what I've got so far:
import sys
import argparse
import math
from scipy import integrate
parser = argparse.ArgumentParser(description='Find the volume of the solid of rotation defined')
parser.add_argument('equation', help='continous function')
parser.add_argument('a', type=float, help='bound \'a\'')
parser.add_argument('b', type=float, help='bound \'b\'')
parser.add_argument('-axis', metavar='x|y', help='axis of revolution')
args = parser.parse_args()
def volume(func, a, b, axis=None):
integral = integrate.quad(func, a, b)
return scipy.py * integral
print volume(args.equation, args.a, args.b)
Any advice will be appreciated
thanks
If there are absolutely no concerns about security risks from letting the user run arbitrary Python code, then you can use eval to create a callable object:
volume(eval('lambda x: %s' % args.equation), args.a, args.b)
You should be able to use eval() on the string you get from your arguments:
>>> f = eval("lambda x: x**2")
>>> f(5)
25

Categories

Resources