def random_walk_2D(np, ns, plot_step): xpositions = zeros(np) ypositions = zeros(np) # extent of the axis in the plot: ymin = -4 ymax = 8 * sqrt(ns) xmax = 3 * sqrt(ns) xmin = -xmax for step in range(ns): for i in range(np): r = random.randint(0, 10) if 0 <= r <= 5: ypositions[i] += 1 elif r == 6: ypositions[i] -= 1 elif 7 <= r <= 8: xpositions[i] += 1 elif 9 <= r <= 10: xpositions[i] -= 1 # plot just every plot_step steps: if (step + 1) % plot_step == 0: plot(xpositions, ypositions, 'ko', axis=[xmin, xmax, ymin, ymax], title='%d researchers after %d months, with ownership of strategy' % \ (np, step+1), hardcopy='tmp_%03d.eps' % (step+1)) return xpositions, ypositions
def random_walk_2D(np, ns, plot_step): xpositions = zeros(np) ypositions = zeros(np) # extent of the axis in the plot: xymax = 3*sqrt(ns); xymin = -xymax NORTH = 1; SOUTH = 2; WEST = 3; EAST = 4 # constants for step in range(ns): for i in range(np): direction = random_number.randint(1, 4) if direction == NORTH: ypositions[i] += 1 elif direction == SOUTH: ypositions[i] -= 1 elif direction == EAST: xpositions[i] += 1 elif direction == WEST: xpositions[i] -= 1 # plot just every plot_step steps: if (step+1) % plot_step == 0: plot(xpositions, ypositions, 'ko', axis=[xymin, xymax, xymin, xymax], title='%d particles after %d steps' % \ (np, step+1), hardcopy='tmp_%03d.eps' % (step+1)) return xpositions, ypositions
def random_walk_2D(np, ns, plot_step): xpositions = zeros(np) ypositions = zeros(np) # extent of the axis in the plot: xymax = 3 * sqrt(ns) xymin = -xymax NORTH = 1 SOUTH = 2 WEST = 3 EAST = 4 # constants for step in range(ns): for i in range(np): direction = random_number.randint(1, 4) if direction == NORTH: ypositions[i] += 1 elif direction == SOUTH: ypositions[i] -= 1 elif direction == EAST: xpositions[i] += 1 elif direction == WEST: xpositions[i] -= 1 # plot just every plot_step steps: if (step + 1) % plot_step == 0: plot(xpositions, ypositions, 'ko', axis=[xymin, xymax, xymin, xymax], title='%d particles after %d steps' % \ (np, step+1), hardcopy='tmp_%03d.eps' % (step+1)) return xpositions, ypositions
def random_walk_2D(np, ns, plot_step): xpositions = zeros(np) ypositions = zeros(np) # extent of the axis in the plot: ymin = -4 ymax = 8 * sqrt(ns) xmax = 3 * sqrt(ns) xmin = -xmax for step in range(ns): for i in range(np): r = random.randint(0, 10) if 0 <= r <= 5: ypositions[i] += 1 elif r == 6: ypositions[i] -= 1 elif 7 <= r <= 8: xpositions[i] += 1 elif 9 <= r <= 10: xpositions[i] -= 1 # plot just every plot_step steps: if (step + 1) % plot_step == 0: plot( xpositions, ypositions, "ko", axis=[xmin, xmax, ymin, ymax], title="%d researchers after %d months, with ownership of strategy" % (np, step + 1), hardcopy="tmp_%03d.eps" % (step + 1), ) return xpositions, ypositions
def test_constant(): k=2.718281828459045 #define functions that give costant solution I=lambda x,y: k q=lambda x,y: 34 + x #define some variables Lx = 10 Ly = 4 T = 3 C = 1. dt= 0.1 #get constant solution Nx = int(round(Lx/dt)) Ny = int(round(Ly/dt)) ue =zeros((Nx+1,Ny+1)) +k u,x,y,t,error=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='vector') print 'Test constant solution. Exercise 3.1' print '||abs(u-ue)||: ', amax(abs(u-ue)) print assert amax(abs(u-ue))<10**(-16)
def solver(T, dt, v0, Cd, rho, A, m, Source=None): """ This is the main solver function for the program. It takes the problem specific variables as arguments, and returns two meshes containing the velocity and time points respectively. """ a = Cd * rho * A / (2 * m) # Set up the constant a for compact code v = zeros(int(T / dt) + 1) # Create the velocity mesh v[0] = v0 g = 9.81 #Initial velocity and the value of gravity acceleration # Description of the functions X(t) and Y(t) is given in the PDF file def X(t): if (Source == None): return -g else: return -g + Source(t + dt / 2.) / m def Y(t): return a #Calculate the velocity at each meshpoint for i in range(1, len(v)): v[i] = skydiving_iterate(v[i - 1], dt * (i - 1), dt, X, Y) return v, linspace(0, T, T / dt + 1)
def constructed_bugs(): k=2.718281828459045 I=lambda x,y: k q=lambda x,y: x+y Lx = 10 Ly = 5 T = 3 C = 1. dt= 0.5 Nx = int(round(Lx/dt)) Ny = int(round(Ly/dt)) ue =zeros((Nx+1,Ny+1)) +k u1,x,y,t=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar',bug='bug1') u2,x,y,t=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar',bug='bug2') u3,x,y,t=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar',bug='bug3') u4,x,y,t=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar',bug='bug4') u5,x,y,t=solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar',bug='bug5') print "Test bugs:" print "bug1 gives error: ",amax(abs(u1-ue)) print "bug2 gives error: ",amax(abs(u2-ue)) print "bug3 gives error: ",amax(abs(u3-ue)) print "bug4 gives error: ",amax(abs(u4-ue)) print "bug5 gives error: ",amax(abs(u5-ue)) print
def __init__(self, f, x): # We want to check for monotonicity i = 0 if 0 in x: raise ValueError('x cannot contain 0') while x[i] == x[i+1]: i+=1 if x[i] > x[i+1]: for j in range(i, len(x)-1): if x[j] < x[j+1]: raise ValueError('No monotonicity') elif x[i] < x[i+1]: for j in range(i, len(x)-1): if x[j] > x[j+1]: raise ValueError('No monotonicity') self.f = f self.x = x from Newton import Newton from scitools.std import zeros g = zeros(len(x)) a = F(f, x[0]) b = dFdx(a) for i in range(len(x)): a.xi = x[i] if i == 0: gamma0 = x[0] else: gamma0 = g[i-1] gamma, n, F_value = Newton(a, gamma0, b) g[i] = gamma self.values = g
def test_convergenceRates(): """ Test for the convergence rates of the solver. The expected result is that the variable r takes the value 2, because the Crank-Nicolson scheme and the geometric average have errors of order dt**2. The final error should then be O(dt**2) which gives r=2. """ dt_start = 1.0 num_dt = 10 E_values = zeros(num_dt) T = 10. g = 9.81 m = 50. Cd = 1.2 rho = 1.0 A = 0.5 a = Cd * rho * A / (2. * m) dt = zeros(num_dt) dt[0] = dt_start for i in range(1, len(dt)): dt[i] = dt[i - 1] / 2. D = -0.39 B = 0.76 C = -0.145 def exact(t): return D * t**3 + B * t + C def src(t): return m * g + m * a * abs( exact(t)) * exact(t) + m * (3 * D * t**2 + B) # Simulate for different timesteps, and store the error in E_values for i in range(num_dt): v, t = solver(T, dt[i], exact(0), Cd, rho, A, m, src) ve = exact(t) diff = v - ve E_values[i] = sqrt(dt[i] * sum(diff**2)) # Calculate r-values corresponding to the error with each different timestep r = zeros(len(E_values) - 1) for i in range(1, len(r)): r[i] = (log(E_values[i - 1] / E_values[i])) / (log(dt[i - 1] / dt[i])) import nose.tools as nt nt.assert_almost_equal(r[-1], 2, delta=0.1)
def d(n): from scitools.std import zeros, sqrt arr = zeros(n) cum_sum = 6 / sqrt(3) for i in range(n): k = i + 1 cum_sum += 6 / sqrt(3) * (-1)**k / (3**k * (2 * k + 1)) arr[i] = cum_sum return arr
def c(n): from scitools.std import zeros arr = zeros(n) cum_sum = 0 for i in range(n): k = i + 1 cum_sum = (cum_sum**4 + 90 * k**(-4))**(.25) arr[i] = cum_sum return arr
def b(n): from scitools.std import sqrt, zeros arr = zeros(n) cum_sum = 0 for i in range(n): k = i + 1 cum_sum = sqrt(cum_sum**2 + 6 * k**(-2)) arr[i] = cum_sum return arr
def a(n): from scitools.std import zeros arr = zeros(n) cum_sum = 0 for i in range(n): k = i + 1 cum_sum += 4. * (-1)**(k + 1) / (2 * k - 1) arr[i] = cum_sum return arr
def e(n): from scitools.std import zeros arr = zeros(n) cum_sum = 16. / 5 - 4. / 239 for i in range(n): k = i + 1 cum_sum += 16.*(-1)**k / (5**(2*k+1) * (2*k+1)) \ - 4. * (-1)**k / (239**(2*k+1) * (2*k+1)) arr[i] = cum_sum return arr
def __call__(self, x): from scitools.std import linspace, sum, zeros,iseq f, a, n = self.f, self.a, self.n h = (x-a)/float(n) I = 0.5*f(a) ar = zeros(len(linspace(1,n-1, n-1))) for i in iseq(1, n-1): ar[i-1] = f(a + i*h) I = sum(ar) I += 0.5*f(x) I *= h return I
def __call__(self, x): from scitools.std import linspace, sum, zeros, iseq f, a, n = self.f, self.a, self.n h = (x - a) / float(n) I = 0.5 * f(a) ar = zeros(len(linspace(1, n - 1, n - 1))) for i in iseq(1, n - 1): ar[i - 1] = f(a + i * h) I = sum(ar) I += 0.5 * f(x) I *= h return I
def test_convergenceRates(): """ Test for the convergence rates of the solver. The expected result is that the variable r takes the value 2, because the Crank-Nicolson scheme and the geometric average have errors of order dt**2. The final error should then be O(dt**2) which gives r=2. """ dt_start = 1.0; num_dt = 10 E_values = zeros(num_dt) T = 10.; g = 9.81; m = 50.; Cd = 1.2; rho = 1.0; A = 0.5; a = Cd*rho*A/(2.*m) dt = zeros(num_dt); dt[0] = dt_start for i in range(1,len(dt)): dt[i] = dt[i-1]/2. D = -0.39; B = 0.76; C = -0.145 def exact(t): return D*t**3 + B*t + C def src(t): return m*g + m*a*abs(exact(t))*exact(t) + m*(3*D*t**2 + B) # Simulate for different timesteps, and store the error in E_values for i in range(num_dt): v, t = solver(T, dt[i], exact(0), Cd, rho, A, m, src) ve = exact(t) diff = v - ve E_values[i] = sqrt(dt[i]*sum(diff**2)) # Calculate r-values corresponding to the error with each different timestep r=zeros(len(E_values)-1) for i in range(1, len(r)): r[i] = (log(E_values[i-1]/E_values[i]))/(log(dt[i-1]/dt[i])) import nose.tools as nt nt.assert_almost_equal(r[-1], 2, delta=0.1)
def forward_leaper(I,a,b,T,dt): """ Solves u'(t) = -a(t)*u(t) + b(t), u(0) = I with a forward difference scheme. """ raise_type(a) raise_type(b) dt = float(dt) N = int(round(T/dt)) # Rounds off to the closest integer T = N*dt # Recalculate the T value based upon the new N value u = zeros(N+1) t = linspace(0,T,N+1) for n in range(0,N): u[n+1] = u[n] - dt*a(dt*n)*u[n] + dt*b(dt*n) return t,u
def forward_leaper(I, a, b, T, dt): """ Solves u'(t) = -a(t)*u(t) + b(t), u(0) = I with a forward difference scheme. """ raise_type(a) raise_type(b) dt = float(dt) N = int(round(T / dt)) # Rounds off to the closest integer T = N * dt # Recalculate the T value based upon the new N value u = zeros(N + 1) t = linspace(0, T, N + 1) for n in range(0, N): u[n + 1] = u[n] - dt * a(dt * n) * u[n] + dt * b(dt * n) return t, u
def plot_forces_parachute(t, v, dt, tp, m, a_first, a_last): """ Function for plotting the forces when running the program with parachute deployment """ plt.figure() drag = zeros(len(v)) for i in range(len(v)): if(i*dt <= tp): drag[i] = -m*a_first*abs(v[i])*v[i] else: drag[i] = -m*a_last*abs(v[i])*v[i] grav = [-m*9.81]*len(v) Boyancy = [1. * 9.81 * 0.1]*len(v) # rho * g * V Fsum = drag+grav+Boyancy plt.plot(t, drag, t, grav, t, Boyancy, t, Fsum) plt.legend(["Drag force", "Gravity force", "Boyancy", "Sum of forces"]) plt.savefig('Parachute_forces.png')
def plot_forces_parachute(t, v, dt, tp, m, a_first, a_last): """ Function for plotting the forces when running the program with parachute deployment """ plt.figure() drag = zeros(len(v)) for i in range(len(v)): if (i * dt <= tp): drag[i] = -m * a_first * abs(v[i]) * v[i] else: drag[i] = -m * a_last * abs(v[i]) * v[i] grav = [-m * 9.81] * len(v) Boyancy = [1. * 9.81 * 0.1] * len(v) # rho * g * V Fsum = drag + grav + Boyancy plt.plot(t, drag, t, grav, t, Boyancy, t, Fsum) plt.legend(["Drag force", "Gravity force", "Boyancy", "Sum of forces"]) plt.savefig('Parachute_forces.png')
def finite_difference(L, Nx, N, dt, C, P_L, P_R): x = linspace(0, L, Nx+1) dx = x[1] - x[0] C = 0.4*C*dt/(dx**2) print C Q = zeros(Nx+1) Q_1 = P_R**2*ones(Nx+1) for n in range(0, N): # Compute u at inner mesh points for i in range(1, Nx): Q[i] = Q_1[i] + C*(Q_1[i-1]**2.5 - 2*Q_1[i]**2.5 + Q_1[i+1]**2.5) # Insert boundary conditions Q[0]=P_L**2; Q[Nx]=P_R**2 # Update u_1 before next step Q_1[:]= Q return sqrt(Q), x
def finite_difference(L, Nx, N, dt, C, P_L, P_R): x = linspace(0, L, Nx+1) dx = x[1] - x[0] C = C*dt/(dx**2) print C P = zeros(Nx+1) P_1 = P_R*ones(Nx+1) for n in range(0, N): # Compute u at inner mesh points for i in range(1, Nx): #print P_1 P[i] = P_1[i] + C*(P_1[i-1]**2 - 2*P_1[i]**2 + P_1[i+1]**2) # Insert boundary conditions P[0]=P_L; P[Nx]=P_R # Update u_1 before next step P_1[:]= P return P, x
def trapezoidal(f, a, x, n): from scitools.std import array, iseq, linspace, zeros x = array(x) I = zeros(len(x)) index = 0 new_sum = 0 old_sum = 0 for i in x: new_sum = 0.5*f(a) h = (i-a)/float(n) new_sum += sum(f(a + array(range(1,n))*h)) new_sum += 0.5*f(i) new_sum *= h new_sum += old_sum I[index] = new_sum index += 1 a = i old_sum = new_sum if len(I) == 1: return I[0] else: return I
def trapezoidal(f, a, x, n): from scitools.std import array, iseq, linspace, zeros x = array(x) I = zeros(len(x)) index = 0 new_sum = 0 old_sum = 0 for i in x: new_sum = 0.5 * f(a) h = (i - a) / float(n) new_sum += sum(f(a + array(range(1, n)) * h)) new_sum += 0.5 * f(i) new_sum *= h new_sum += old_sum I[index] = new_sum index += 1 a = i old_sum = new_sum if len(I) == 1: return I[0] else: return I
def test_constant(): k = 2.718281828459045 #define functions that give costant solution I = lambda x, y: k q = lambda x, y: 34 + x #define some variables Lx = 10 Ly = 4 T = 3 C = 1. dt = 0.1 #get constant solution Nx = int(round(Lx / dt)) Ny = int(round(Ly / dt)) ue = zeros((Nx + 1, Ny + 1)) + k u, x, y, t, error = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='vector') print 'Test constant solution. Exercise 3.1' print '||abs(u-ue)||: ', amax(abs(u - ue)) print assert amax(abs(u - ue)) < 10**(-16)
def solver(T, dt, v0, Cd, rho, A, m, Source=None): """ This is the main solver function for the program. It takes the problem specific variables as arguments, and returns two meshes containing the velocity and time points respectively. """ a = Cd*rho*A/(2*m) # Set up the constant a for compact code v = zeros(int(T/dt) + 1) # Create the velocity mesh v[0] = v0; g = 9.81;#Initial velocity and the value of gravity acceleration # Description of the functions X(t) and Y(t) is given in the PDF file def X(t): if(Source == None): return -g else: return -g + Source(t+dt/2.)/m def Y(t): return a #Calculate the velocity at each meshpoint for i in range(1,len(v)): v[i] = skydiving_iterate(v[i-1], dt*(i-1), dt, X, Y) return v, linspace(0, T, T/dt +1)
def test_plug(): #define function that give q=lambda x,y: 1 #define some variables Lx = 10 Ly = 3 T = 1 C = 1 dt= 0.1 #get constant solution Nx = int(round(Lx/dt)) Ny = int(round(Ly/dt)) ue =zeros((Nx+1,Ny+1)) #define initial function def I(x,y): if abs(x-Lx/2.)<0.5: return 2.1 else: return 0 #solve numerically u,x,y,t,err = solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar') #find exact solution at time T x1 = x+T x2 = x-T for i in range(Nx+1): for j in range(Ny+1): ue[i,j]=0.5*(I(x1[i],0) + I(x2[i],0)) #calculate error at time t=T e1 = amax(abs(u-ue)) #Do the exact same for plug wave in y direction: def I(x,y): if abs(y-Ly/2.)<0.5: return 2.1 else: return 0 #Numerical solution u,x,y,t,err = solver(I,None,None,q,0,Lx,Ly,dt,T,C,1,mode='scalar') #find exact solution at time T y1 = x+T y2 = x-T for i in range(Nx+1): for j in range(Ny+1): ue[i,j]=0.5*(I(0,y1[j]) + I(0,y2[j])) #calculate error at time t=T e2 = amax(abs(u-ue)) print 'Plug error in x ||u(x,y,T)-ue(x,y,T)||: ',e1 print 'Plug error in y ||u(x,y,T)-ue(x,y,T)||: ',e2 print assert e1<10**(-16) and e2<10**(-16)
def test_undampedWaves(): #define constants given in exercise A = 1 mx=7. my=2. #define function that give q=lambda x,y: 1 #define some variables Lx = 3 Ly = 1.3 T = 1 C = 0.5 dt= 0.1 #define omega so equation holds w=pi*sqrt((mx/Lx)**2 +(my/Ly)**2) #help varabeles kx = pi*mx/Lx ky = pi*my/Ly #Exact solution ue = lambda x,y,t: A*cos(x*kx)*cos(y*ky)*cos(t*w) #initial condition so we get result we want. I = lambda x,y: A*cos(x*kx)*cos(y*ky) #factor dt decreeses per step step=0.5 #number of steps I want to do val=5 #array to store errors E=zeros(val) for i in range(val): v='vector' #solve eqation u,x,y,t,e=solver(I,None,None,q,0,Lx,Ly,dt*step**(i),T,C,1,mode=v,ue=ue) E[i]=e #find convergence rate between diffrent dt values r =zeros(val-1) r = log(E[1:]/E[:-1])/log(step) print "Test convergence for undamped waves:" for i in range(val): if i==0: print "dt: ",dt," Error: ",E[i] else: print "dt: ",dt*step**(i)," Error: ",E[i], "rate of con.: ", r[i-1] #requiere close to 2 in convergence rate for last r. assert abs(r[-1]-2)<0.01
""" Exercise 5.2: Fill arrays; loop version Author: Weiyun Lu """ from scitools.std import sqrt, pi, exp, zeros h = lambda x: (1 / (sqrt(2 * pi))) * exp(-0.5 * x**2) n = 8.0 / 40 #length of each subinterval xlist = zeros(41, float) hlist = zeros(41, float) for i in range(41): xlist[i] = -4 + i * n hlist[i] = h(xlist[i]) pairs = zip(xlist, hlist) print pairs
def solver(I, V_, f_, c, Lx, Ly, Nx, Ny, dt, T, b, user_action=None, version='scalar', skip_every_n_frame=10, show_cpu_time=False,display_warnings=True, plotting=False): order = 'C' # Store arrays in a column-major order (in memory) x = linspace(0, Lx, Nx+1) # mesh points in x dir y = linspace(0, Ly, Ny+1) # mesh points in y dir dx = x[1] - x[0] dy = y[1] - y[0] xv = x[:,newaxis] # for vectorized function evaluations yv = y[newaxis,:] # Assuming c is a function: c_ = zeros((Nx+1,Ny+1), order='c') for i,xx in enumerate(x): for j,yy in enumerate(y): c_[i,j] = c(xx,yy) # Loop through x and y with indices i,j at the same time c_max = c_.max() # Pick out the largest value from c(x,y) q = c_**2 stability_limit = (1/float(c_max))*(1/sqrt(1/dx**2 + 1/dy**2)) if dt <= 0: # shortcut for max time step is to use i.e. dt = -1 safety_factor = -dt # use negative dt as safety factor extra_factor = 1 # Easy way to make dt even smaller dt = safety_factor*stability_limit*extra_factor elif dt > stability_limit and display_warnings: print '\nWarning: (Unless you are testing the program), be aware that' print 'dt: %g is currently exceeding the stability limit: %g\n' %(dt, stability_limit) Nt = int(round(T/float(dt))) t = linspace(0, Nt*dt, Nt+1) # mesh points in time dt2 = dt**2 # Constants for simple calculation A = (1 + b*dt/2)**(-1) B = (b*dt/2 - 1) dtdx2 = dt**2/(2*dx**2) dtdy2 = dt**2/(2*dy**2) # Make f(x,y,t) and V(x,y) ready for computation with different schemes if f_ is None or f_ == 0: f = (lambda x, y, t: 0) if version == 'scalar' else \ lambda x, y, t: zeros((xv.shape[0], yv.shape[1])) else: if version == 'scalar': f = f_ if V_ is None or V_ == 0: V = (lambda x, y: 0) if version == 'scalar' else \ lambda x, y: zeros((xv.shape[0], yv.shape[1])) else: if version == 'scalar': V = V_ if version == 'vectorized': # Generate and fill matrices for first timestep f = zeros((Nx+1,Ny+1), order=order) V = zeros((Nx+1,Ny+1), order=order) f[:,:] = f_(xv,yv,0) V[:,:] = V_(xv,yv) u = zeros((Nx+1,Ny+1), order=order) # solution array u_1 = zeros((Nx+1,Ny+1), order=order) # solution at t-dt u_2 = zeros((Nx+1,Ny+1), order=order) # solution at t-2*dt Ix = range(0, u.shape[0]) # Index set notation Iy = range(0, u.shape[1]) It = range(0, t.shape[0]) import time; t0 = time.clock() # for measuring CPU time # Load initial condition into u_1 if version == 'scalar': for i in Ix: for j in Iy: u_1[i,j] = I(x[i], y[j]) else: # use vectorized version u_1[:,:] = I(xv, yv) if user_action is not None: if plotting: user_action(u_1, x, xv, y, yv, t, 0, skip_every_n_frame) else: user_action(u_1, x, xv, y, yv, t, 0) # Special formula for first time step n = 0 # First step requires a special formula, use either the scalar # or vectorized version (the impact of more efficient loops than # in advance_vectorized is small as this is only one step) if version == 'scalar': u,cpu_time = advance_scalar(u, u_1, u_2, q, f, x, y, t, n, A, B, dt2, dtdx2,dtdy2, V, step1=True) else: u,cpu_time = advance_vectorized(u, u_1, u_2, q, f, t, n, A, B, dt2, dtdx2,dtdy2, V, step1=True) if user_action is not None: if plotting: user_action(u, x, xv, y, yv, t, 1, skip_every_n_frame) else: user_action(u_1, x, xv, y, yv, t, 1) # Update data structures for next step u_2, u_1, u = u_1, u, u_2 # Time loop for all later steps for n in It[1:-1]: if version == 'scalar': # use f(x,y,t) function u,cpu_time = advance_scalar(u, u_1, u_2, q, f, x, y, t, n, A, B, dt2, dtdx2,dtdy2) if show_cpu_time: percent = (float(n)/It[-2])*100.0 sys.stdout.write("\rLast step took: %.3f sec with [scalar-code]. Computation is %d%% " %(cpu_time,percent)) sys.stdout.flush() else: # Use vectorized code f[:,:] = f_(xv, yv, t[n]) # must precompute the matrix f u,cpu_time = advance_vectorized(u, u_1, u_2, q, f, t, n, A, B, dt2, dtdx2,dtdy2) if show_cpu_time: percent = (float(n)/It[-2])*100.0 sys.stdout.write("\rLast step took: %.5f sec with [vec-code]. Computation is %d%% " %(cpu_time,percent)) sys.stdout.flush() if user_action is not None: if plotting: if user_action(u, x, xv, y, yv, t, n+1, skip_every_n_frame): break else: if user_action(u, x, xv, y, yv, t, n+1): break # Update data structures for next step #u_2[:] = u_1; u_1[:] = u # safe, but slower u_2, u_1, u = u_1, u, u_2 # Important to set u = u_1 if u is to be returned! t1 = time.clock() # dt might be computed in this function so return the value return dt, t1 - t0
def test_plug(): #define function that give q = lambda x, y: 1 #define some variables Lx = 10 Ly = 3 T = 1 C = 1 dt = 0.1 #get constant solution Nx = int(round(Lx / dt)) Ny = int(round(Ly / dt)) ue = zeros((Nx + 1, Ny + 1)) #define initial function def I(x, y): if abs(x - Lx / 2.) < 0.5: return 2.1 else: return 0 #solve numerically u, x, y, t, err = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar') #find exact solution at time T x1 = x + T x2 = x - T for i in range(Nx + 1): for j in range(Ny + 1): ue[i, j] = 0.5 * (I(x1[i], 0) + I(x2[i], 0)) #calculate error at time t=T e1 = amax(abs(u - ue)) #Do the exact same for plug wave in y direction: def I(x, y): if abs(y - Ly / 2.) < 0.5: return 2.1 else: return 0 #Numerical solution u, x, y, t, err = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar') #find exact solution at time T y1 = x + T y2 = x - T for i in range(Nx + 1): for j in range(Ny + 1): ue[i, j] = 0.5 * (I(0, y1[j]) + I(0, y2[j])) #calculate error at time t=T e2 = amax(abs(u - ue)) print 'Plug error in x ||u(x,y,T)-ue(x,y,T)||: ', e1 print 'Plug error in y ||u(x,y,T)-ue(x,y,T)||: ', e2 print assert e1 < 10**(-16) and e2 < 10**(-16)
def test_undampedWaves(): #define constants given in exercise A = 1 mx = 7. my = 2. #define function that give q = lambda x, y: 1 #define some variables Lx = 3 Ly = 1.3 T = 1 C = 0.5 dt = 0.1 #define omega so equation holds w = pi * sqrt((mx / Lx)**2 + (my / Ly)**2) #help varabeles kx = pi * mx / Lx ky = pi * my / Ly #Exact solution ue = lambda x, y, t: A * cos(x * kx) * cos(y * ky) * cos(t * w) #initial condition so we get result we want. I = lambda x, y: A * cos(x * kx) * cos(y * ky) #factor dt decreeses per step step = 0.5 #number of steps I want to do val = 5 #array to store errors E = zeros(val) for i in range(val): v = 'vector' #solve eqation u, x, y, t, e = solver(I, None, None, q, 0, Lx, Ly, dt * step**(i), T, C, 1, mode=v, ue=ue) E[i] = e #find convergence rate between diffrent dt values r = zeros(val - 1) r = log(E[1:] / E[:-1]) / log(step) print "Test convergence for undamped waves:" for i in range(val): if i == 0: print "dt: ", dt, " Error: ", E[i] else: print "dt: ", dt * step**( i), " Error: ", E[i], "rate of con.: ", r[i - 1] #requiere close to 2 in convergence rate for last r. assert abs(r[-1] - 2) < 0.01
def test_manufactured(): A = 1 B = 0 mx = 1 my = 1 b = 1 c = 1.1 #define some variables Lx = 2. Ly = 2. T = 1 C = 0.3 dt = 0.1 #help varabeles kx = pi * mx / Lx ky = pi * my / Ly w = 1 #Exact solution ue = lambda x, y, t: A * cos(x * kx) * cos(y * ky) * cos(t * w) * exp(-c * t) I = lambda x, y: A * cos(x * kx) * cos(y * ky) V = lambda x, y: -c * A * cos(x * kx) * cos(y * ky) q = lambda x, y: x**2 + y**2 f = lambda x, y, t: A * ( -b * (c * cos(t * w) + w * sin(t * w)) * cos(kx * x) * cos(ky * y) + c **2 * cos(kx * x) * cos(ky * y) * cos(t * w) + 2 * c * w * sin( t * w) * cos(kx * x) * cos(ky * y) + kx**2 * (x**2 + y**2) * cos(kx * x) * cos(ky * y) * cos(t * w) + 2 * kx * x * sin(kx * x) * cos(ky * y) * cos(t * w) + ky**2 * (x**2 + y**2) * cos(kx * x) * cos(ky * y) * cos(t * w) + 2 * ky * y * sin(ky * y) * cos(kx * x) * cos(t * w) - w**2 * cos(kx * x) * cos( ky * y) * cos(t * w)) * exp(-c * t) #factor dt decreeses per step step = 0.5 #number of steps I want to do val = 5 #array to store errors E = zeros(val) for i in range(val): v = 'vector' #solve eqation u, x, y, t, e = solver(I, V, f, q, b, Lx, Ly, dt * step**(i), T, C, 8, mode=v, ue=ue) E[i] = e #find convergence rate between diffrent dt values r = zeros(val - 1) r = log(E[1:] / E[:-1]) / log(step) print print "Convergence rates for manufactured solution:" for i in range(val): if i == 0: print "dt: ", dt, " Error: ", E[i] else: print "dt: ", dt * step**( i), " Error: ", E[i], "rate of con.: ", r[i - 1] #requiere "close" to 2 in convergence rate for last r. assert abs(r[-1] - 2) < 0.5
def test_manufactured(): A=1 B=0 mx=1 my=1 b=1 c=1.1 #define some variables Lx = 2. Ly = 2. T = 1 C = 0.3 dt= 0.1 #help varabeles kx = pi*mx/Lx ky = pi*my/Ly w=1 #Exact solution ue = lambda x,y,t: A*cos(x*kx)*cos(y*ky)*cos(t*w)*exp(-c*t) I = lambda x,y: A*cos(x*kx)*cos(y*ky) V = lambda x,y: -c*A*cos(x*kx)*cos(y*ky) q = lambda x,y: x**2+y**2 f = lambda x,y,t:A*(-b*(c*cos(t*w) + w*sin(t*w))*cos(kx*x)*cos(ky*y) + c**2*cos(kx*x)*cos(ky*y)*cos(t*w) + 2*c*w*sin(t*w)*cos(kx*x)*cos(ky*y) + kx**2*(x**2 + y**2)*cos(kx*x)*cos(ky*y)*cos(t*w) + 2*kx*x*sin(kx*x)*cos(ky*y)*cos(t*w) + ky**2*(x**2 + y**2)*cos(kx*x)*cos(ky*y)*cos(t*w) + 2*ky*y*sin(ky*y)*cos(kx*x)*cos(t*w) - w**2*cos(kx*x)*cos(ky*y)*cos(t*w))*exp(-c*t) #factor dt decreeses per step step=0.5 #number of steps I want to do val=5 #array to store errors E=zeros(val) for i in range(val): v='vector' #solve eqation u,x,y,t,e=solver(I,V,f,q,b,Lx,Ly,dt*step**(i),T,C,8,mode=v,ue=ue) E[i]=e #find convergence rate between diffrent dt values r =zeros(val-1) r = log(E[1:]/E[:-1])/log(step) print print "Convergence rates for manufactured solution:" for i in range(val): if i==0: print "dt: ",dt," Error: ",E[i] else: print "dt: ",dt*step**(i)," Error: ",E[i], "rate of con.: ", r[i-1] #requiere "close" to 2 in convergence rate for last r. assert abs(r[-1]-2)<0.5
def constructed_bugs(): k = 2.718281828459045 I = lambda x, y: k q = lambda x, y: x + y Lx = 10 Ly = 5 T = 3 C = 1. dt = 0.5 Nx = int(round(Lx / dt)) Ny = int(round(Ly / dt)) ue = zeros((Nx + 1, Ny + 1)) + k u1, x, y, t = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar', bug='bug1') u2, x, y, t = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar', bug='bug2') u3, x, y, t = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar', bug='bug3') u4, x, y, t = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar', bug='bug4') u5, x, y, t = solver(I, None, None, q, 0, Lx, Ly, dt, T, C, 1, mode='scalar', bug='bug5') print "Test bugs:" print "bug1 gives error: ", amax(abs(u1 - ue)) print "bug2 gives error: ", amax(abs(u2 - ue)) print "bug3 gives error: ", amax(abs(u3 - ue)) print "bug4 gives error: ", amax(abs(u4 - ue)) print "bug5 gives error: ", amax(abs(u5 - ue)) print
from matplotlib.pyplot import * from scitools.std import zeros, exp n = 15 x = 3 #linspace(0,n,1000) z = zeros(n) for j in range(n): z[j] = (2 * j + 1) * exp((-j * (j + 1)) / (x)) plot(range(n), z) show()
nbins = int(file.readline()) # first line is number of bins rho = float(file.readline()) # second is density of system N = int(file.readline()) # third line is number of particles in system file.readline() # read fourth and fifth line file.readline() E_kin = [] # kinetic energy E_pot = [] # potetial energy E_tot = [] # total energy of the system T = [] # Temperataure P = [] # Pressure r_msq_t = [] # Mean square displacement t = [] # time nsy = [] # not sure yet :-) binz = zeros(nbins) timeiterations = 0 for line in file: values = line.split() Temp = values[0] time = values[1] Ek = values[2] Ep = values[3] Pressure = values[4] rmsq = values[5] allbins = values[6:] T.append(float(Temp)) t.append(float(time)) E_kin.append(float(Ek))
nbins = int(file.readline()) # first line is number of bins rho = float(file.readline()) # second is density of system N = int(file.readline()) # third line is number of particles in system file.readline() # read fourth and fifth line file.readline() E_kin = [] # kinetic energy E_pot = [] # potetial energy E_tot = [] # total energy of the system T = [] # Temperataure P = [] # Pressure r_msq_t = [] # Mean square displacement t = [] # time nsy = [] # not sure yet :-) binz = zeros(nbins) timeiterations = 0 for line in file: values = line.split() Temp = values[0] time = values[1] Ek = values[2] Ep = values[3] Pressure = values[4] rmsq = values[5] allbins = values[6:] T.append(float(Temp)) t.append(float(time)) E_kin.append(float(Ek))
""" Exercise 5.6: Simulate by hand a vectorized expression Author: Weiyun Lu """ from scitools.std import array, sin, cos, exp, zeros x = array([0, 2]) t = array([1, 1.5]) y = zeros((2, 2)) f = lambda x, t: cos(sin(x)) + exp(1.0 / t) for i in range(2): for j in range(2): y[i][j] = f(x[i], t[j]) print y