I am working with complex functions in sympy (python 3) and am having trouble getting sympy to simplify the equations. In particular I can't get sympy to use Euler's Identity to break up the complex exponential into real and imaginary parts. Here is my code:
import sympy as sym
from sympy import I, init_printing
# setup printing
init_printing()
# complex potential cylinder in uniform flow
U,z,R,theta=sym.symbols('U z R theta')
F=U*z+U/z
# complex velocity cylinder in uniform flow
compVel=sym.diff(F,z)
exp1=sym.sympify('R*exp(I*theta)')
compVel=compVel.subs(z,exp1)
print(compVel)
phi,psi=sym.symbols('phi psi')
phi=sym.re(compVel)
psi=sym.im(compVel)
print(phi)
print(psi)
When I run this code the output is:
U - U*exp(-2*I*theta)/R**2
re(U) - re(U*exp(-2*I*theta)/R**2)
im(U) - im(U*exp(-2*I*theta)/R**2)
Am I missing something or is sympy not powerful enough to do recognize this simplification? Thanks in advance!
I figured it out; #Stelios is correct but in addition when you use sympify you must pass a dictionary with the local variables that the expression contains.
exp1=sym.sympify('R*exp(I*theta)',locals={'R':R,'theta':theta})
Related
I have the following code, but it shows error:
IntegrationWarning: The maximum number of subdivisions (50) has been achieved.
If increasing the limit yields no improvement it is advised to analyze
the integrand in order to determine the difficulties. If the position of a
local difficulty can be determined (singularity, discontinuity) one will
probably gain from splitting up the interval and calling the integrator
on the subranges. Perhaps a special-purpose integrator should be used.
potC=sc.integrate.quad(lambda r: Psi(r,n2)*(-1/r)Psi(r,n1)(r**2),0,np.inf)
How to fix it?
import scipy as sc
import numpy as np
def Psi(r,n):
return 2*np.exp(-r/n)*np.sqrt(n)*sc.special.hyp1f1(1-n, 2, 2*r/n)/n**2
def p(n1,n2):
potC=sc.integrate.quad(lambda r: Psi(r,n2)*(-1/r)*Psi(r,n1)*(r**2),0,np.inf)
pot=potC[0]
return pot
print(p(15,15))
The error literally says what your problem is. Your function is not "well behaved" in some regions.
For example with n = 15 and r = 50 your special.hyp1f1(-14, 2, 2*50/15) result in NaN. I am not familiar with this function, so I do not know if this is the expected behaviour, but this is what happens.
You can try to isolate these points and exclude them from the integration (if you know lower and upper bounds of the function's value (if it is defined) you can also update the expected error of your integration) and just integrate in the well behaved regions.
If it is a bug in scipy, then please report it to them.
Ps.: Tested with scipy 1.8.0
Ps2.: With some reading I found, that you can get the values correctly, if you do your calculations with complex number, so the following code gives you a value:
import scipy as sc
from scipy import integrate
from scipy import special
import numpy as np
def Psi(r,n):
r = np.array(r,dtype=complex)
return 2*np.exp(-r/n)*np.sqrt(n)*special.hyp1f1(1-n, 2, 2*r/n)/n**2
def p(n1,n2):
potC=integrate.quad(lambda r: Psi(r,n2)*(-1/r)*Psi(r,n1)*(r**2),0,np.inf)
pot=potC[0]
return pot
print(p(15,15))
I am Currently working on some optimization problem which involves non-linear constraint. The problem is as follows :
I need to perform either of the two minimizations shown in image in python. I found library scipy which has optimize.minimize() function but I am unable to fit in the Non-Linear constraint using scipy.NonLinearConstraint. Can anyone guide? How to solve this? Is there also a way to solve it using some homotopy function given in any of the libraries? I have tried (adding constraint for the alternative one)as:
con = lambda A,x,y : np.matmul(A,x) - y
nlc = NonlinearConstraint(con, 0, epsilon)
So, I finally could solve the above optimization by using spgl1 solver in python. It can be used as shown below:
from spgl1 import spgl1, spg_bp, spg_bpdn
#x01 = psueodinverse of A multiplied by y
x,resid,grad,info = spgl1(A, y, tau = tau, sigma = epsilon, x0 = x01, iter_lim = 150)
one can refer about the above solver at github link or pypi link
If the price charged for a crayon is p cents, then x thousand crayons
will be sold in a certain school store, where p(x)= 122-x/34 .
Using Python, calculate how many crayons must be sold to maximize
revenue.
I can solve this by hand much easily, the only problem is how can I do it using plain Python? I am using IDLE (Python GUI). I am new to Python and haven't downloaded any external libraries. Any help will be greatly appreciated.
What I've done up to this point is
import math
def f(x):
return (122-(x/34.0))
def g(x):
return x*f(x)
def h(x):
return (122-(2*x/34.0))
Use SymPy. It's simple, beautiful and powerful.
You can write down your equations with simpify(), like that:
p = simpify('122 - x/34')
And define symbols for symbolic evaluation with Symbol() and symbols().
With that you can do things like simply use solve() function for any given equation. i.e. x + 4 = 2x:
res = solve('x + 4 - 2*x')
It's pretty much the tool I use for any math work with python.
So, you should go and download an external library for this, as it's not functionality that python makes easy to implement natively. Also, if you're serious about doing mathematical computation in python I would suggest switching operating systems to something like OSX or linux, simply because compiling old FORTRAN libraries (required for much performant mathematical computing) is a huge pain on Windows.
You have to make use of the scipy library here, which has an optimize module. Specifically I would suggest using the optimize.minimize_scalar function. Docs can be found here.
>>> from scipy.optimize import minimize_scalar
>>> def g(x):
... return -(x*(122 - (x/34))) # inverse because you're minimizing.
>>> minimize_scalar(g, bounds=(1, 10000), method='bounded')
status: 0
nfev: 6
success: True
fun: -126514.0
x: 2074.0
message: 'Solution found.'
When I run this program, I get no solution at the end, but there should be a solution ( I believe). Any idea what I am doing wrong? If you take away the Q from e2 equation it seems to work correctly.
#!/usr/bin/python
from sympy import *
a,b,w,r = symbols('a b w r',real=True,positive=True)
L,K,Q = symbols('L K Q',real=True,positive=True)
e1=K
e2=(K*Q/2)**(a)
print solve(e1-e2,K)
It works if we do the following:
Set Q=1 or,
Change e2 to e2=(K*a)(Q/2)**(a)
I would still like it to work in the original way though, as my equations are more complicated than this.
This is just a deficiency of solve. solve is based mostly on heuristics, so sometimes it isn't able to figure out how to solve an equation when it's given in a particular form. The workaround here is to just call expand_power_base on the expression, since SymPy is able to solve K - K**a*(Q/2)**a:
In [8]: print(solve(expand_power_base(e1-e2),K))
[(2/Q)**(a/(a - 1))]
It's also worth pointing out that the result of [] from solve does not in any way mean that there are no solutions, only that solve was unable to find any. See the first note at http://docs.sympy.org/latest/tutorial/solvers.html.
I'm trying to solve an equation in python using SymPy. I have a generated equation (something like function = y(8.0-(y**3.0)) which I use with SymPy to create a new equation like this: eq = sympy.Eq(function, 2) which outputs y(8.0-(y**3.0)) == 2. but sympy.solve(eq) doesn't seem to work.
>>> from sympy import Eq, Symbol as sym, solve
>>> y = sym('y')
>>> eqa = Eq(y(8.0-(y**3.0)), 8)
>>> solve(eqa)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/lib/pymodules/python2.6/sympy/solvers/solvers.py", line 332, in solve
result = tsolve(f, *symbols)
File "/usr/lib/pymodules/python2.6/sympy/solvers/solvers.py", line 716, in tsolve
raise NotImplementedError("Unable to solve the equation.")
NotImplementedError: Unable to solve the equation.
thanks for reading.
Yours is a non linear equation ... So you can use optimize.fsolve for it. For further details look for the function in this tutorial scipy
(I don't know why you mention scipy in your question when you use sympy in your code. I'll assume you are using sympy.)
Sympy can solve this equation if you specify an integer power for y (ie y**3.0 changed to y**3).
The following works for me using Sympy 0.6.7.
from sympy import Eq, Symbol, solve
y = Symbol('y')
eqn = Eq(y*(8.0 - y**3), 8.0)
print solve(eqn)
Assuming you mean you were trying to use sympy, as opposed to scipy, then you can get Sympy (works with v0.7.2+) to solve it by making a small adjustment to way you defined your equation - you just need to put a multiplication operator (*) in between the first 'y' and the '('. It doesn't appear to matter whether you specify the power as a float or not (but it's possible it was required in 0.6.7).
from sympy import Eq, var, solve
var('y')
eq = Eq(y*(8.0-(y**3.0)), 8)
solve(eq)
For nonlinear equations, you should use sympy.solvers.nsolve to solve it numerically, except for some special cases where a more specific and appropriate solver may exist (e.g. tsolve).
For example, the following script should output 1.2667664310254.
from sympy import Symbol
from sympy.solvers import nsolve
from sympy import sin, tan
theta = Symbol('theta')
print nsolve(tan(theta)/(1+1*sin(theta)) - 4.0**2/9.81, theta, (1.2,))
This is a non-linear equation. What you need to look for is a root finding algorithm in SciPy.