``````

In [2]:

import numpy as np
import matplotlib.pyplot as plt
import matplotlib
%matplotlib inline
#matplotlib.rcParams['figure.figsize'] = (7.0, 5.5)

from astropy import units
from galpy.orbit import Orbit
from FerrersPotential import FerrersPotential as FP
from galpy.potential import PlummerPotential as PP

``````
``````

In [13]:

%%prun -s cumulative
pmw = FP(amp = 1, a = 8*units.kpc, b = 0.35, c = 0.2375, normalize = True, omegab = 10.*units.km/units.s/units.kpc)
ps = FP(amp = 1, a = 8*units.kpc, b = 1., c = 1., normalize = True, omegab = 10.*units.km/units.s/units.kpc)
ts = np.linspace(0,34,500)
omwa = Orbit(vxvv=[1,0.25,0.7,0,0.0,0]) #[R,vR,vT,z,vz,phi]
omwb = Orbit(vxvv=[1,0.25,0.7,0,0.0,0]) #[R,vR,vT,z,vz,phi]

#omwa.integrate(ts, pmw, method = 'leapfrog')
#omwb.integrate(ts, ps, method = 'leapfrog')

``````
``````

``````
``````

In [7]:

matplotlib.rcParams['figure.figsize'] = (7.0, 7.)
omwb.plot(d1 = 'x', d2 = 'y', overplot = False, color = 'red')
omwa.plot(d1 = 'x', d2 = 'y', overplot = True, color = '#00AF3F')

``````
``````

``````
``````

In [192]:

ts = np.linspace(0,500,5000)
omwf = Orbit(vxvv=[1,0.25,0.6,0,0.0,0]) #[R,vR,vT,z,vz,phi]
#omwg = Orbit(vxvv=[1,0.25,0.6,0,0.0,0]) #[R,vR,vT,z,vz,phi]
#omwfd = Orbit(vxvv=[1,0.25001,0.6,0,0.0,0]) #[R,vR,vT,z,vz,phi]

omwf.integrate(ts, pmw, method = 'leapfrog')
#omwfd.integrate(ts, pmw, method = 'leapfrog')
#omwg.integrate(ts, ps, method = 'leapfrog')

``````
``````

In [193]:

omwf.plot(d1 = 'x', d2 = 'y')

``````
``````

``````
``````

In [552]:

omwg.integrate(ts, ps, method = 'leapfrog')

``````
``````

In [50]:

matplotlib.rcParams['figure.figsize'] = (10., 10.)
#omwg.plot('k.', d1 = 'R', d2 = 'vR', overplot = False, color = 'crimson')
omwf.plot('-', d1 = 'x', d2 = 'y', overplot = False, color = '#00AF3F')
#omwfd.plot('-', d1 = 'x', d2 = 'y', overplot = True, color = 'blue')

``````
``````

``````
``````

In [297]:

omwc = Orbit(vxvv=[1,0.25,0.7,0,0.0,0])
tsc = np.linspace(0,3,50)
omwc.integrate(tsc, pmw, method = 'leapfrog')
omwc.plot(d1 = 'x', d2 = 'y', overplot = False, color = 'red')

``````
``````

``````
``````

In [298]:

print(omwc.R(tsc[-1]), omwc.vR(tsc[-1]), omwc.vT(tsc[-1]), omwc.z(tsc[-1]), omwc.vz(tsc[-1]), omwc.phi(tsc[-1]))

``````
``````

0.750649738829 0.740785260631 -0.0236964417435 0.0 0.0 4.60170920819

``````
``````

In [312]:

icon = np.array([0.750649738829, 0.740785260631, -0.0236964417435, 0.0, 0.0, 4.60170920819])
omwx = Orbit(vxvv=icon)
tsx = np.linspace(0,3,50)
omwx.integrate(tsx, pmw, method = 'leapfrog')
omwx.plot(d1 = 'x', d2 = 'y', overplot = False, color = 'navy')
omwc.plot(d1 = 'x', d2 = 'y', overplot = True, color = 'red')
plt.xlim(-1.2,1.2)
plt.ylim(-2,0.75)

omw = Orbit(vxvv=[0.750649738829, 0.740785260631, -0.0236964417435, 0.0, 0.0, 4.60170920819])
tsc = np.linspace(3,10,100)
omw.integrate(tsc, pmw, method = 'leapfrog')
omw.plot(d1 = 'x', d2 = 'y', overplot = True, color = 'gold', marker = 'x')

omw = Orbit(vxvv=[1,0.25,0.7,0,0.0,0])
tsc = np.linspace(0,10,200)
omw.integrate(tsc, pmw, method = 'leapfrog')
omw.plot(d1 = 'x', d2 = 'y', overplot = True, color = 'red', linewidth = 0.8)

``````
``````

``````
``````

In [304]:

omwc = Orbit(vxvv=[1,0.25,0.7,0,0.0,0])
tsc = np.linspace(0,6,100)
omwc.integrate(tsc, pmw, method = 'leapfrog')
omwc.plot(d1 = 'x', d2 = 'y', overplot = False, color = 'red')

``````
``````

``````
``````

In [527]:

pp = PP(normalize = True)
op = Orbit(vxvv = [1.,.4,.93, 0.])
tsp = np.linspace(0,10,200)
op.integrate(tsp, pp,method = 'leapfrog')

``````
``````

In [ ]:

matplotlib.rcParams['figure.figsize'] = (7.0, 7.)
op.plot(d1 = 'x', d2 = 'y', overplot = False)

``````

# ====================== useful functions =========================

``````

In [3]:

def rot(omega, t):
temp = [[np.cos(t*omega), np.sin(t*omega)], [-np.sin(t*omega), np.cos(t*omega)]]
return np.array(temp)

def inrotframe(x,y, ts, potential):
xy = np.zeros([len(x),2])
xy[:,0] = x
xy[:,1] = y
omega = potential.OmegaP()
xrot, yrot = np.zeros(len(ts)), np.zeros(len(ts))
for i in range(len(ts)):
xrot[i],yrot[i] = np.dot(xy[i],rot(omega, ts[i]))
return xrot, yrot

``````
``````

In [4]:

def allorbits(x,y, n):
xo = [x[n*i] for i in range(int(len(x)/n))]
xo1 = [x[n*i+1] for i in range(int(len(x)/n))]
xo2 = [x[n*i+2] for i in range(int(len(x)/n))]
yo = [y[n*i] for i in range(int(len(x)/n))]
yo1 = [y[n*i+1] for i in range(int(len(x)/n))]
yo2 = [y[n*i+2] for i in range(int(len(x)/n))]
if n==4:
xo3 = [x[n*i+3] for i in range(int(len(x)/n))]
yo3 = [y[n*i+3] for i in range(int(len(x)/n))]
return [xo,yo],[xo1,yo1],[xo2,yo2],[xo3,yo3]
if n==5:
xo3 = [x[n*i+3] for i in range(int(len(x)/n))]
yo3 = [y[n*i+3] for i in range(int(len(x)/n))]
xo4 = [x[n*i+4] for i in range(int(len(x)/n))]
yo4 = [y[n*i+4] for i in range(int(len(x)/n))]
return [xo,yo],[xo1,yo1],[xo2,yo2],[xo3,yo3],[xo4,yo4]
if n==6:
xo3 = [x[n*i+3] for i in range(int(len(x)/n))]
yo3 = [y[n*i+3] for i in range(int(len(x)/n))]
xo4 = [x[n*i+4] for i in range(int(len(x)/n))]
yo4 = [y[n*i+4] for i in range(int(len(x)/n))]
xo5 = [x[n*i+5] for i in range(int(len(x)/n))]
yo5 = [y[n*i+5] for i in range(int(len(x)/n))]
return [xo,yo],[xo1,yo1],[xo2,yo2],[xo3,yo3],[xo4,yo4],[xo5,yo5]
if n==7:
xo3 = [x[n*i+3] for i in range(int(len(x)/n))]
yo3 = [y[n*i+3] for i in range(int(len(x)/n))]
xo4 = [x[n*i+4] for i in range(int(len(x)/n))]
yo4 = [y[n*i+4] for i in range(int(len(x)/n))]
xo5 = [x[n*i+5] for i in range(int(len(x)/n))]
yo5 = [y[n*i+5] for i in range(int(len(x)/n))]
xo6 = [x[n*i+6] for i in range(int(len(x)/n))]
yo6 = [y[n*i+6] for i in range(int(len(x)/n))]
return [xo,yo],[xo1,yo1],[xo2,yo2],[xo3,yo3],[xo4,yo4],[xo5,yo5],[xo6,yo6]
return [xo,yo],[xo1,yo1],[xo2,yo2]

``````

# =========================== GALI =============================

``````

In [5]:

""" #1
name: devolist
input:
list of initial conditions for the orbit [R,vR,vT,z,vz,phi]; icon
in other than first iteration also 'indev', a list which contains normalized deviation vectors from previous
iteration to be applied to the current state of the Orbit
output:
list of initial conditions for deviated orbit; devos
"""
def devolist(icon, indev=None):
devos = []
if indev == None:
reldev = 0.01
dorb = icon[:]
for i in range(len(icon)):
dorb = icon[:]
dorb[i] += dorb[i]*reldev
if icon[i] != dorb[i]:
devos.append(dorb)
else:
for i in range(len(indev)):
dorb = icon[:]
dorb = list(np.array(dorb)+np.array(indev[i]))
devos.append(dorb)
return devos
# test
print(devolist([1,0.25,0.7,0.1,5.2,0.1]))#, indev = [[1,0,0,0,0,0],[0,1,0,0,0,0],[0,2,1,0,0,0]]))

``````
``````

[[1.01, 0.25, 0.7, 0.1, 5.2, 0.1], [1, 0.2525, 0.7, 0.1, 5.2, 0.1], [1, 0.25, 0.707, 0.1, 5.2, 0.1], [1, 0.25, 0.7, 0.101, 5.2, 0.1], [1, 0.25, 0.7, 0.1, 5.252, 0.1], [1, 0.25, 0.7, 0.1, 5.2, 0.101]]

``````
``````

In [6]:

""" #2
name: evolveorbit
input:
list of initial conditions for the orbit [R,vR,vT,z,vz,phi]; icon
final time; tf
potential; pot
output:
list of orbit parameters in time tf;
"""
x = []
y = []
def evolveorbit(icon, ti, tau, pot): #############
global x
global y
o = Orbit(vxvv=icon) # [R,vR,vT,z,vz,phi]
tf = ti+tau
ts = np.linspace(ti,tf,100)
o.integrate(ts, pot, method = 'leapfrog')
x.append(o.x(ts[0]))
y.append(o.y(ts[0]))
return [o.R(tf),o.vR(tf),o.vT(tf),o.z(tf),o.vz(tf),o.phi(tf)] #for full 3D orbit

``````
``````

In [7]:

""" #3
name: dvector
input:
evolved orbit o and deviated orbit d
output:
deviation vector w
"""
def dvector(o,d):
return np.array(d)-np.array(o)

``````
``````

In [8]:

""" #4
name: matrixnorm
input:
list of devitation vectors (np.arrays) to be normalized; wj
output:
np.array of normalized deviation vectors; a
"""
def matrixnorm(wj):
a = np.array(wj) # creates matrix consisting of k deviation vectors of dimension N
k = len(a)
for j in range(k):
a[j] = abs(a[j] / np.linalg.norm(a[j]))
return a

``````
``````

In [9]:

""" #5
name: galivalue
input:
np.array of deviation vectors; a
output:
value of gali at a specific time
"""
def galivalue(a):
aT = np.transpose(a)
s = np.linalg.svd(aT)[1] # creates array of singular values
return np.prod(s) # returns product of singular values ~ gali

``````
``````

In [10]:

"""
name: gali
input:
initial conditions for the orbit
renormalization time ~ timestep
potential in which the Orbit is inspected
output:
current value of gali, new IC for the Orbit, normalized dev. vectors in matrix for next step
"""
def gali(o, ti, tau, potential, w=None):
if type(w) == type(None):
v = devolist(list(o), indev = w)#deviated orbits from the Orbit
else:
v = w
newo = evolveorbit(o, ti, tau, potential) #evolves the Orbit
wj = []
for dorbit in v:
temp = evolveorbit(dorbit + o*(type(w) != type(None)), ti, tau, potential) #evolves the deviated orbits to time tau
wj.append(dvector(o=newo,d=temp)) #creates list of deviation vectors in time tau
a = matrixnorm(wj) #normalizes the matrix containing deviation vectors in time tau
return galivalue(a), newo, np.array(wj) #returns value of gali, new IC for the Orbit, x-normalized-x dev. vectors in matrix

``````
``````

In [11]:

"""
name: galievol
input:
initial conditions for the orbit
renormalization time ~ timestep
potential in which the Orbit is inspected
maximum time Tm and small treshold value of the GALI Gm
output:
42 (and list of GALI values during the integration)
"""
def galievol(o,tau, potential, Tm, Gm):
global x
global y
x,y = [],[]
galis = np.zeros([1+int(Tm/tau),2]) # array large enough
continuing = True # stopping flag
i = 1 # counter
w = None #initial setting
while continuing:
galis[i-1][1], newo, a = gali(o, tau*i, tau, potential, w)
galis[i-1][0] = tau*i
if galis[i-1][1]<Gm:
print('if this code works, the orbit is chaotic')
continuing = False
return galis[:i-1][:]
if i*tau > Tm:
print('time reached treshold, orbit is regular if this code works')
continuing = False
return galis[:][:]
i += 1
o = newo
w = a

``````
``````

In [ ]:

icon = np.array([1.,0.25,0.6,0.,0.,0.])
tau = 0.01
Tm = 100
Gm = 10**-16
results = galievol(icon, tau, pmw, Tm, Gm)

``````
``````

In [ ]:

matplotlib.rcParams['figure.figsize'] = (15.0, 5.5)
plt.plot((results[:,0]), np.log10(results[:,1])) # for IC [1.,0.25,0.6,0.,0.,0.], chaotic orbit
plt.xlabel(r'\$t\$', fontsize = 15)
plt.ylabel(r'\$log_{10}\,GALI_3\$', fontsize = 15)

``````
``````

In [25]:

# DON'T TOUCH IT ANNA!
matplotlib.rcParams['figure.figsize'] = (15.0, 5.5)
plt.plot((resultsx1[:,0]), np.log10(resultsx1[:,1])) # for IC [0.5,0.3,0.3,0.,0.,np.pi/50], regular orbit
plt.xlabel(r'\$t\$', fontsize = 15)
plt.ylabel(r'\$log_{10}\,GALI_3\$', fontsize = 15)

``````
``````

Out[25]:

<matplotlib.text.Text at 0x7f9418e7ca90>

``````
``````

In [21]:

orb = Orbit(vxvv = [0.5,0.3,0.3,0.,0.,np.pi/50])
timespan = np.linspace(0,5,60)
orb.integrate(timespan, pmw, method = 'leapfrog')

``````
``````

In [22]:

matplotlib.rcParams['figure.figsize'] = (7, 7)
orb.plot(d1 = 'x', d2 = 'y')
#plt.xlim(-0.5,0.5)
#plt.ylim(-0.5,0.5)

``````
``````

``````
``````

In [17]:

matplotlib.rcParams['figure.figsize'] = (10, 10)
[xo,yo],[xo1,yo1],[xo2,yo2],[xo3,yo3], [xo4,yo4] = allorbits(x,y,n=5)
plt.plot(xo[:500], yo[:500], c = 'crimson')
plt.plot(xo1[:500], yo1[:500], c = 'blue')
plt.plot(xo2[:500], yo2[:500], c = 'orange')
plt.plot(xo3[:500], yo3[:500], c = '#00AF3F')
plt.plot(xo4[:500], yo4[:500], c = 'purple')
#plt.plot(xo5[:500], yo5[:500], c = 'dodgerblue')
#plt.plot(xo6[:500], yo6[:500], c = 'gold')
#plt.xlim(-0.5,0.5)
#plt.ylim(-0.5,0.5)
plt.show()

``````
``````

``````
``````

In [162]:

for i in range(len(results)):
if x[i]>0.45:
print(x[i], results[i])

``````
``````

In [ ]:

ps = FP(amp = 1, a = 8*units.kpc, b = 1., c = 1., normalize = True, omegab = 10.*units.km/units.s/units.kpc)
icon = np.array([.2,-.6,.5, 0.,0.,0.]) # 11:54 -
tau = 10**-2
Tm = 1000
Gm = 10**-16
results = galievol(icon, tau, ps, Tm, Gm)

``````
``````

In [ ]:

matplotlib.rcParams['figure.figsize'] = (15.0, 5.5)
plt.scatter((results[:,0]), np.log10(results[:,1]))
plt.xlabel(r'\$t\$', fontsize = 15)
plt.ylabel(r'\$log_{10}\,GALI_3\$', fontsize = 15)
#plt.xlim(100,110)

``````
``````

In [ ]:

%%prun -s cumulative
Tm=300. # 4:28 - 4:36 for 300 pts
tau = 5*10**-2
Gm = 10**-16
pmw = FP(amp = 1, a = 8*units.kpc, b = 0.35, c = 0.2375, normalize = True, omegab = 10.*units.km/units.s/units.kpc)
icon = np.array([1.,0.25,0.6,0.,0,0])
results8 = galievol(icon, tau, pmw, Tm, Gm)

``````
``````

In [ ]:

matplotlib.rcParams['figure.figsize'] = (15.0, 5.5)
plt.scatter((results8[:,0]), np.log10(results8[:,1]),marker = '+', c= 'crimson') #initial deviation 1%
plt.xlabel(r'\$t\$', fontsize = 15)
plt.ylabel(r'\$log_{10}\,GALI_3\$', fontsize = 15)
#plt.xlim(0,100)

``````