Using scipy.integrate.ode to solve protoplanetary hydrostatic equilibria - python

I have written code to solve the protoplanetary hydrostatic equilibria equations using first order euler method, and the results are as expected. I now want to rewrite it using fourth order Runge-Kutta solution, which is builtin to scipy.integrate.ode
Expected result, attained by using a custom written euler method:
import numpy as np
import matplotlib.pyplot as plt
from scipy.integrate import ode
universalGasConstant = 8.31
gravitationalConstant = 6.67 * 10**-11
astronomicalUnit = 1.5 * (10**11)
coreMass = 5.9 * 10**24
sunMass = 2 * (10**30)
coreRadius = 0
coreDensity = 5500.0
semiMajorAxis = 5 * astronomicalUnit
gasMeanMolecularMass = 2.3 * 10**-3
coreRadius = (coreMass / ((4 / 3) * np.pi * coreDensity))**(1 / 3)
print('coreradius is', coreRadius)
hillSphere = (1**-4)*(semiMajorAxis) * (((coreMass) / (3 * sunMass))**(1 / 3))
print('hillsphere is', hillSphere)#THIS IS THE HILLSPHERE
numberOfSlices = 100000000 #NUMBER OF SLICES
deltaRadius = hillSphere / numberOfSlices
print('slice length is', deltaRadius)
#gravitationalForce = ((gravitationalConstant * coreMass) /
#(coreRadius + (deltaRadius)))
sunSurfaceTemperature = 5800
sunRadius = 6.96 * 10**8
equilibriumTemperature = sunSurfaceTemperature * \
(sunRadius / (2 * semiMajorAxis))**(1 / 2)
print('equilibrium temperature at', semiMajorAxis,
'metres is', equilibriumTemperature, 'kelvin')
pressureAtRadius = 0
initialDensity = 10.0 #INITIAL DENSITY
densityAtRadius = 0
muOverRT = gasMeanMolecularMass/(equilibriumTemperature * universalGasConstant)
print('muOverRT is', muOverRT)
totalMass = coreMass
densityAtRadius = initialDensity
def function(y, r):
totalMass = y[0]
distanceFromCOG = y[1]
# the differential equations
dRhodr = -(((gravitationalConstant*totalMass*
densityAtRadius*muOverRT))/(distanceFromCOG**2))
dMdr = 4*np.pi*gravitationalConstant*densityAtRadius
#dPdr = (1/(muOverRT))*dRhodr
return [dRhodr, dMdr]
distanceFromCOG = coreRadius+np.linspace(0,numberOfSlices) #number of points
initialDensity = [0,0]
solution = ode(function,initialDensity,distanceFromCOG).set_integrator('vode', method = 'dopri5')
plt.plot(solution)
solution.set_integrator('dopri5')

Related

Numerical instability in python

I am trying to make several plots for a project of mine using the following code:
import pprint
import scipy
import scipy.linalg # SciPy Linear Algebra Library
import numpy as np
from scipy.linalg import lu , lu_factor, lu_solve
from scipy.integrate import quad
import matplotlib.pyplot as plt
#Solving the equations for the Prandtl case
K = 100
alpha = 0.1
visc = 5
diff = 5
N = 0.01
L = 5000
height = 250
subdivisions = 100
tick = 10
points = np.arange(0,L/2+tick,tick)
def H(y):
return ( height * (1 + np.cos(2 * np.pi * y/L)) )
def Bsfc(y):
return 0.1
final_system = []
b=[]
for q in range(-K,K+1):
equation1 = []
equation2 = []
equation3 = []
Aki = []
Cki = []
Dki = []
for k in range(-K,K+1):
R = 2 * N**2 * np.cos(alpha)**2 / (visc * diff) * (k * np.pi / L)**2
Q = N**2 * np.sin(alpha)**2 / (3 * visc * diff)
S1 = abs(R + np.sqrt(Q**3 + R**2) )**(1/3)
S2 = - abs( np.sqrt(Q**3 + R**2) -R )**(1/3)
phi = np.sqrt(S1**2 + S2**2 - S1*S2)
Lk = np.arccos(- (S1 + S2)/ (2 * phi) )
m1 = - np.sqrt(S1 + S2)
m2 = - np.sqrt(phi) * np.exp(1j * Lk/2)
m3 = m2.conjugate()
def f1r(y):
return (np.exp(m1 * H(y)) * np.cos(2 * (q - k) * np.pi * y / L) ).real
def f1i(y):
return (np.exp(m1 * H(y)) * np.cos(2 * (q - k) * np.pi * y / L) ).imag
gamma1 = 2/L * (quad(f1r,0,L/2,limit=subdivisions)[0] + quad(f1i,0,L/2,limit=subdivisions)[0]*1j)
def f2r(y):
return (np.exp(m2 * H(y)) * np.cos(2 * (q - k) * np.pi * y / L) ).real
def f2i(y):
return (np.exp(m2 * H(y)) * np.cos(2 * (q - k) * np.pi * y / L) ).imag
gamma2 = 2/L * (quad(f2r,0,L/2,limit=subdivisions)[0] + quad(f2i,0,L/2,limit=subdivisions)[0]*1j)
if k == 0:
equation1.append(2 * gamma2.real)
Cki.append(k)
equation1.append(-2 * gamma2.imag)
Dki.append(k)
else:
equation1.append(gamma1)
Aki.append(k)
equation1.append(2 * gamma2.real)
Cki.append(k)
equation1.append(-2 * gamma2.imag)
Dki.append(k)
if q != 0:
if k == 0:
equation2.append(0)
equation2.append(0)
else:
equation2.append(k * gamma1 / (m1**3) )
equation2.append(2 * k * (gamma2 / (m2**3) ).real)
equation2.append(-2 * k * (gamma2 / (m2**3) ).imag)
if k == 0:
equation3.append(2 * (m2**2 * gamma2).real)
equation3.append(-2 * (m2**2 * gamma2).imag)
else:
equation3.append(m1**2 * gamma1)
equation3.append(2 * (m2**2 * gamma2).real)
equation3.append(-2 * (m2**2 * gamma2).imag)
final_system.append(equation1)
def f4r(y):
return (Bsfc(y) * np.cos(2 * q * np.pi * y / L) ).real
def f4i(y):
return (Bsfc(y) * np.cos(2 * q * np.pi * y / L) ).imag
b.append(2/L * (quad(f4r,0,L/2,limit=subdivisions)[0] + quad(f4i,0,L/2,limit=subdivisions)[0]*1j))
if q != 0:
final_system.append(equation2)
b.append(0)
final_system.append(equation3)
b.append(0)
final_system = np.array(final_system)
b=np.array(b)
#LU solver
P, Ls, U = scipy.linalg.lu(final_system)
Bl = np.linalg.inv(P) # b
Z = np.linalg.solve(Ls,Bl)
X = np.linalg.solve(U,Z)
print (np.allclose(final_system # X, b))
#Getting the values for Ak, Ck and Dk
strings = []
for k in range(-K,K+1):
if k != 0:
strings.append('A')
strings.append('R')
strings.append('I')
Ak = []
Rk = []
Ik = []
for k in range(0,len(X)):
if 'A' in strings[k]:
Ak.append(X[k])
if 'R' in strings[k]:
Rk.append(X[k])
if 'I' in strings[k]:
Ik.append(X[k])
Ck=[]
for k in range(0,len(Rk)):
Ck.append(Rk[k] + Ik[k] * 1j)
Ck = np.array(Ck)
Dk = Ck.conjugate()
Ak = np.array(Ak)
#Getting the Buoyancy value
z = np.arange(0,2010,10)
y = np.arange(-L,L+10,10)
Y,Z = np.meshgrid(y,z)
B = np.ones_like(Y)*[0]
for k in range(-K,K+1):
R = 2 * N**2 * np.cos(alpha)**2 / (visc * diff) * (k * np.pi / L)**2
Q = N**2 * np.sin(alpha)**2 / (3 * visc * diff)
S1 = abs(R + np.sqrt(Q**3 + R**2) )**(1/3)
S2 = - abs( np.sqrt(Q**3 + R**2) -R )**(1/3)
phi = np.sqrt(S1**2 + S2**2 - S1*S2)
Lk = np.arccos(- (S1 + S2)/ (2 * phi) )
m1 = - np.sqrt(S1 + S2)
m2 = -np.sqrt(phi) * np.exp(1j * Lk/2)
m3 = m2.conjugate()
if k != 0:
B = B + ( Ak[Aki.index(k)] * np.exp(m1 * Z) * np.exp(2j * (k) * np.pi * Y / L) )
B = B + ( ( Ck[Cki.index(k)] * np.exp(m2 * Z) + Dk[Dki.index(k)] * np.exp(m3 * Z) ) * np.exp(2j * (k) * np.pi * Y / L) )
for k in range(0,B.shape[0]):
for t in range(0,B.shape[1]):
if Z[k][t] < H(Y[k][t]):
B[k][t] = np.nan
if Z[k][t] == H(Y[k][t]):
print (B[k][t], "B value at the ground")
if abs(Z[k][t] - H(Y[k][t])) < 0.1:
if B[k][t] > 0.101:
print (B[k][t],'error -------------------------------------------------')
# print (B[k][t], Z[k][t], H(Y[k][t]), Y[k][t], '-----------------------------------------------------------------------------' )
Bp = Bsfc(Y) * np.exp(-Z * np.sqrt(N * np.sin(alpha) ) / (4*visc*diff)**(1/4) ) * np.cos(np.sqrt(N*np.sin(alpha)) /((4*visc*diff)**(1/4))*Z )
##Plotting the buoyancy
fig = plt.figure(figsize=(10,10)) # create a figure
plt.rcParams.update({'font.size':16})
plt.title('Buoyancy')
plt.contourf(Y,Z,B,np.arange(-0.2,0.201,0.001),cmap='seismic')
#plt.contourf(Y,Z,B,cmap='seismic')
plt.colorbar(label='1/s')
plt.xlabel("Y axis")
plt.ylabel("Height")
plt.xlim([-L,L])
plt.ylim([0,1500])
plt.show()
The following plot shows a run that yielded a good result:
Buoyancy
However, when I increase the "height" parameter, I start getting unstable results, which I suspect occurs because of numerical instabilities:
Buoyancy unstable
Is there a way to increase numerical precision in python? I have experimented a bit with numpy.double, but with unsuccessful results so far.
Thanks
I guess you'll find your answer here on Stackoverflow
In the standard library, the decimal module may be what you're looking
for. Also, I have found mpmath to be quite helpful...

How to add latent heat term in FiPy?

I have been trying to simulate Two Temperature Model using fipy
the math of the model:
C_e(∂T_e)/∂t=∇[k_e∇T_e ]-G(T_e-T_ph )+ A(r,t)
C_ph(∂T_ph)/∂t=∇[k_ph∇T_ph] + G(T_e-T_ph)
the source supposed to heat the electrons T_e, then the heat transferred to phonons T_ph through G, when T_ph reach melting point for example 2700 K, some of heat (360000 J) goes as latent heat before melting.
here is my code:
from fipy.tools import numerix
import scipy
import fipy
import numpy as np
from fipy import CylindricalGrid1D
from fipy import Variable, CellVariable, TransientTerm, DiffusionTerm, Viewer, LinearLUSolver, LinearPCGSolver, \
LinearGMRESSolver, ImplicitDiffusionTerm, Grid1D, ImplicitSourceTerm
## Mesh
nr = 50
dr = 1e-7
# r = nr * dr
mesh = CylindricalGrid1D(nr=nr, dr=dr, origin=0)
x = mesh.cellCenters[0]
# Variables
T_e = CellVariable(name="electronTemp", mesh=mesh,hasOld=True)
T_e.setValue(300)
T_ph = CellVariable(name="phononTemp", mesh=mesh, hasOld=True)
T_ph.setValue(300)
G = CellVariable(name="EPC", mesh=mesh)
t = Variable()
# Material parameters
C_e = CellVariable(name="C_e", mesh=mesh)
k_e = CellVariable(name="k_e", mesh=mesh)
C_ph = CellVariable(name="C_ph", mesh=mesh)
k_ph = CellVariable(name="k_ph", mesh=mesh)
C_e = 4.15303 - (4.06897 * numerix.exp(T_e / -85120.8644))
C_ph = 4.10446 - 3.886 * numerix.exp(-T_ph / 373.8)
k_e = 0.1549 * T_e**-0.052
k_ph =1.24 + 16.29 * numerix.exp(-T_ph / 151.57)
G = numerix.exp(21.87 + 10.062 * numerix.log(numerix.log(T_e )- 5.4))
# Boundary conditions
T_e.constrain(300, where=mesh.facesRight)
T_ph.constrain(300, where=mesh.facesRight)
# Source 𝐴(𝑟,𝑡) = 𝑎𝐷(𝑟)𝜏−1 𝑒−𝑡/𝜏 , 𝐷(𝑟) = 𝑆𝑒 exp (−𝑟2/𝜎2)/√2𝜋𝜎2
sig = 1.0e-6
tau = 1e-15
S_e = 35
d_r = (S_e * 1.6e-9 * numerix.exp(-x**2 /sig**2)) / (numerix.sqrt(2. * 3.14 * sig**2))
A_t = numerix.exp(-t/tau)
a = (numerix.sqrt(2. * 3.14)) / (3.14 * sig)
A_r = a * d_r * tau**-1 * A_t
eq0 = (
TransientTerm(var=T_e, coeff=C_e) == \
DiffusionTerm(var=T_e, coeff=k_e) - \
ImplicitSourceTerm(coeff=G, var=T_e) + \
ImplicitSourceTerm(var=T_ph, coeff=G) + \
A_r)
eq1 = (TransientTerm(var=T_ph, coeff=C_ph) == DiffusionTerm(var=T_ph, coeff=k_ph) + ImplicitSourceTerm(var=T_e, coeff=G) - ImplicitSourceTerm(coeff=G, var=T_ph))
eq = eq0 & eq1
dt = 1e-18
steps = 7000
elapsed = 0.
vi = Viewer((T_e, T_ph), datamin=0., datamax=2e4)
for step in range(steps):
T_e.updateOld()
T_ph.updateOld()
vi.plot()
res = 1e100
dt *= 1.01
count = 0
while res > 1:
res = eq.sweep(dt=dt, underRelaxation=0.5)
print(t, res)
t.setValue(t + dt)
As I understood I can include the latent heat as source term as sink in eq1, or add a gaussian peak to C_ph and the peak center should be around melting point.
I have no idea which one is better and more stable, I have no idea how to implement any one of them .
please help me with that
Based on the comments (please edit that into the question), change eq1 to
eq1 = (TransientTerm(var=T_ph, coeff=C_ph)
== DiffusionTerm(var=T_ph, coeff=k_ph)
+ ImplicitSourceTerm(var=T_e, coeff=G)
- ImplicitSourceTerm(coeff=G, var=T_ph)
+ (1/numerix.sqrt(2*numerix.pi * sig2)) * numerix.exp(-(T_ph - 1850)**2 / 2 * sig2)))
It will be evaluated explicitly, but it will update whenever T_ph updates.

Vectors in 3D 3 Body Problem, Error that vector needs x, y, dy, and dx

I used the skeleton of a code modeling the three body problem. However, I am trying to figure out why the vectors will not work. I have commented them out (lines 56-60) so that I can see the rest of the program working. I'll attach the code so you can see the error. It is an error telling me the specs for a vector, but I don't see why the input wouldn't work. Thanks !
import numpy as np
import matplotlib.pyplot as plt
from vpython import *
from IPython.display import display
scene = display(title = "Earth's Orbit", width = 500, height = 500, range = 3.e11)
# #
# scene.autoscale = 0 # Turn off auto scaling of display
#
# Define the Sun and the Earth objects.
#
sun = sphere(color = color.yellow)
earth = sphere(color = color.blue)
venus = sphere(color = color.red)
# Gravitational constant (Nm**2/kg**2)
G = 6.67 * 10 ** -11
sun.pos = vector(0, 0, 0) # Initial Sun position (m)
earth.pos = vector(0, -149.6 * 10 ** 7, 149.6 * 10 ** 9) # Initial Earth position (m)
venus.pos = vector(1.0820948 * 10 **11, -1.0820948 * 10 **11, 0) # Initial Venus position (m)
rhat = -norm(earth.pos) # Getting Magnitude, probably going touse normalized vectors for simplicity
sun.mass = 2 * 10 ** 30 # Mass of the Sun (kg)
earth.mass = 6 * 10 ** 24 # Mass of the Earth (kg)
venus.mass = 4.867 * 10 ** 24 # Mass of Venus (kg)
earth.velocity = vector(30 * 10 ** 3, 0, 0)
venus.velocity = vector(35.02 * 10 ** 3, 0, 0)
# Initial velocity in seconds (THIS IS WHERE WE CAN CHANGE THINGS UP BUT BE SENSIBLE)
dt = 86000
#
total = 0 #Initializes the totl elpsed time
#
# Scale factors to control how big the Earth and Sun are drawn in the display
#
sun.scale = 1e1
earth.scale = 5e2
venus.scale = earth.scale
#
sun.radius = 7.e8 * sun.scale
earth.radius = 6.4e6 * earth.scale
venus.radius = 6.052e6 * venus.scale
#
#Initialize the momentum and path of the Earth
#
earth.momentum = earth.mass * earth.velocity # momentum of Earth
venus.momentum = venus.mass * venus.velocity # momentum of Venus
earth.trail = curve(color = earth.color) # Defines Earth's path
# Set initial position of the Earth
earth.trail.append(pos = earth.pos)
#
# Define an arrow thata points from the origin to the Earth
#
##rearrow = arrow(pos = (0, 0, 0) ,axis = earth.pos,
## color = earth.color, shaftwidth = 1e6)
##momentumArrow = arrow(pos = earth.pos, axis = earth.momentum,
## color = earth.color, shaftwidth = 1e6)
#
tmax = 3600 * 24 * 364.25 # Number of seconds in a year
#
# Start of the loop structure
#
while(True):
#
rate(100) # limit the loop to a maximum of 100 times per second
#
# Fill in the next 3 lines with the correct expressions
earthToSun = -norm(earth.pos)
venusToSun = -norm(venus.pos)
earthToVenus = -norm(earth.pos - venus.pos)
# Compute the force that the Sun exerts on the Earth and added Venus's influence
earth.force = ((G * earth.mass * sun.mass) / (mag(earth.pos)) ** 2 * rhat
+ G * venus.mass * earth.mass / mag(earth.pos - venus.pos) ** 2 * earthToVenus)
earth.momentum = earth.momentum + earth.force * \
dt # Update Earth's momentum
# Let's updaate Earth's position
earth.pos = earth.pos + (earth.momentum / earth.mass) * dt
forceEarth = (G * earth.mass * venus.mass) / (mag(earth.pos - venus.pos)) ** 2 * earthToVenus
forceSun = G * venus.mass * sun.mass / (mag(venus.pos)) ** 2 * venusToSun
venus.force = forceEarth + forceSun
venus.momentum += venus.force * dt
venus.pos += (venus.momentum / venus.mass) * dt
momentumArrow.pos = earth.pos
momentumArrow.axis = earth.momentum * 10 ** -18
earth.trail.append(pos = earth.pos) # Updates Earth' trail
rearrow.axis = earth.pos # Move Earth's position arrow
total = total + dt #Increment the Time
#
# Print
#
print(earth.pos)
(0,0,0) is not a vector, it's a Python tuple. You need to say vector(0,0,0) or vec(0,0,0).

solve_ivp error : Required step size is less than spacing between numbers

I have been trying to implement a model of unstable glacier flow in Python, solving the ODEs in scipy, with the RK45 method.
The original model publication can be found here.
Now, I think I understand what is going on with the error but I cannot find a way to fix it.
I don't know if it comes from my implementation or from the ODEs themselves.
I've been through the units several times, checking that all times were in seconds, all distances in meters and so on.
I've tried with different t_eval and even different values of certain constants, but not been able to solve my problem.
I started by creating a class with all constants.
import numpy as np
import scipy.integrate
import matplotlib.pyplot as plt
import astropy.units as u
SECONDS_PER_YEAR = 3600*24*365.15
class Cst:
#Glenn's flow Law
A = 2.4e-25
n = 3.
#Standard physical constants
g = 10.#*(u.m)*(u.second**-2)
rho = 916#*(u.kilogram*(u.m**-3))
#Thermodynamics
cp = 2000#**(u.Joule)*(u.kilogram**-1)*(u.Kelvin**-1)
L = 3.3e5#*(u.Joule)*(u.kilogram**-1)
k = 2.1 #*(u.Watt)*(u.m**-1)*'(u.Kelvin**-1)'
DDF = 0.1/SECONDS_PER_YEAR #*(u.m)*(u.yr**-1)*'(u.Kelvin**-1)
K = 2.3e-47#*((3600*24*365.15)**9)#*((u.kilogram**-5)*(u.m**2)*(u.second**9))
C = 9.2e13#*((u.Pascal)*(u.Joule)*(u.m**-2))
#Weertman friction law
q = 1
p = 1/3
R = 15.7#*((u.m**(-1/3))*(u.second**(1/3)))
d = 10#*u.m
sin_theta = 0.05
Tm = 0+273.15 #*u.Kelvin
T_offset = -10+273.15#*u.Kelvin
w = 0.6 #u.m
Wc = 1000.#*u.m
#Velocities
u1 = 0/SECONDS_PER_YEAR #m/s
u2 = 100/SECONDS_PER_YEAR # m/s
#Dimensionless parameters
alpha = 5.
Then I declared the problem-specific parameters specified in the paper:
#All values are from Table 1
a0 = 1./SECONDS_PER_YEAR#* m/s (u.meter*((u.second)**-1))
l0 = 10000#*(u.meter)
E0 = 1.8e8#(Cst.g*Cst.sin_theta*a0*(l0**2))/(Cst.L*Cst.K))**(1/Cst.alpha)#*(u.Joule/u.m**2)
T0 = 10#E0/(Cst.rho*Cst.cp*Cst.d)#*u.Kelvin
w0 = 0.6#E0/(Cst.rho*Cst.L)#*u.m
N0 = 0.5#Cst.C/E0#*u.Pascal
H0 = 200 #((Cst.R*(Cst.C**Cst.q)*(a0**Cst.p)*(l0**Cst.p))/(Cst.rho*Cst.g*Cst.sin_theta*(E0**Cst.q)))**(1/(Cst.p+1))
t0 = 200 #H0/a0
u0 = 50/SECONDS_PER_YEAR#((Cst.rho*Cst.g*Cst.sin_theta*(E0**Cst.q)*a0*l0)/(Cst.R*(Cst.C**Cst.q)))**(1/(Cst.p+1))
Q0 = (Cst.g*Cst.sin_theta*a0*(l0**2))/Cst.L
S0 = ((Cst.g*Cst.sin_theta*a0*(l0**2)*Cst.Wc)/(Cst.L*Cst.K*((Cst.rho*Cst.g*Cst.sin_theta)**(1/2))))**(3/4)
lamb = ((2.*Cst.A*(Cst.rho*Cst.g*Cst.sin_theta)**Cst.n)*(H0**(Cst.n+1)))/((Cst.n+2)*u0)
chi = N0/(Cst.rho*Cst.g*H0)
gamma = 0.41
kappa = 0.7
phi = 0.2
delta = 66
mu = 0.2
Define the model :
def model(t, x):
#Initial values
H_hat = x[0]
E_hat = x[1]
#Thickness
H = H_hat*H0
#Enthalpy
E_hat_plus = max(E_hat, 0)
E_hat_minus = min(E_hat, 0)
E_plus = E_hat_plus*E0
E_minus = E_hat_minus*E0
a_hat = 1.
theta_hat = Cst.sin_theta/Cst.sin_theta
l_hat =l0/l0
T_a = 0+273.15
T = -10+273.15
# Equation 3
m_hat = (Cst.DDF*(T_a-Cst.T_offset))/a0
S_hat = 0.
T_a_hat = T_a/T0
#Equation A7
if E_plus > 0:
N = min(H/chi, 1./E_plus)
else:
N = H/chi
phi = min(1., E_plus/(H/chi))
#Equation 8
inv_p = 1./Cst.p
u = (Cst.rho*Cst.g*Cst.sin_theta/Cst.R * H * (N**(-Cst.q)))**inv_p
#Equation A7
beta = min(max(0, (u-Cst.u1)/(Cst.u2-Cst.u1)), 1)
#Equation A4
dHdt_hat = (
a_hat - m_hat
+ 1./l_hat*(
theta_hat**inv_p
* H_hat**(1.+inv_p)
* N**(-Cst.q*inv_p)
+ lamb*(theta_hat**Cst.n)
)
)
#Equation A5
dEdt_hat = 1./mu*(
theta_hat**(1+inv_p) * H_hat**(1.+inv_p) * N**(-Cst.q*inv_p)
+ gamma
+ kappa*(E_hat_minus - T_a_hat)/H_hat
- 1./l_hat * (
theta_hat * E_hat_plus**Cst.alpha
+ phi * theta_hat**(1./2) * S_hat**(4/3.)
)
+ delta * beta * m_hat
)
return [dHdt_hat, dEdt_hat]
And finally call it :
tmax = 200*SECONDS_PER_YEAR# *u.years
t = np.linspace(0, tmax, 10000)
sol = scipy.integrate.solve_ivp(model, t_span=[t[0], t[-1]], y0=[1, 1], t_eval=t, method='RK23')
print(sol)
Which yields
message: 'Required step size is less than spacing between numbers.'
nfev: 539
njev: 0
nlu: 0
sol: None
status: -1
success: False
t: array([0.])
t_events: None
y: array([[1.],
[1.]])
y_events: None

New to python and looking for a hint to solve a syntax error

I'm trying to figure out whats wrong about the following code sample. Running this I end up with a syntax error on line 18. Can't figure out why though.
import numpy as np
from scipy.integrate import odeint
import matplotlib.pyplot as plt
def hex(x, A):
Tf = x[0]
Tk = x[1]
Nk = 0.1
Tg = 300
b = 0.2
ag = 30
k = 20
Hvap = 80000
cpg = 100
cpk = 600
ng = 30
cpf = 600
q = k * (Tf-Tk)
n1 = ng * b * np.log(y2f/y2b)
dTfdA = (ag * phi * (Hvap/cpg + (Tg-Tf)/(1-np.exp(-phi))) - q / (Nf * cpf)
dTkdA = -q / (Nk * cpk)
return [dTfdA, dTkdA]
I think you're missing a bracket
dTfdA = (ag * phi * (Hvap/cpg + (Tg-Tf)/(1-np.exp(-phi))) - q / (Nf * cpf)
to
dTfdA = (ag * phi * (Hvap/cpg + (Tg-Tf)/(1-np.exp(-phi))) - q / (Nf * cpf))
You should write the equation as:
dTkdA = 0 - q / (Nk * cpk)

Categories

Resources