Buckets:
| # -*- coding: utf-8 -*- | |
| """ | |
| Created on Sat Jul 05 09:54:39 2014 | |
| @author: rlabbe | |
| """ | |
| from __future__ import division, print_function | |
| import matplotlib.pyplot as plt | |
| from scipy.integrate import ode | |
| import math | |
| import numpy as np | |
| from numpy import random, radians, cos, sin | |
| class BallTrajectory2D(object): | |
| def __init__(self, x0, y0, velocity, theta_deg=0., g=9.8, noise=[0.0,0.0]): | |
| theta = radians(theta_deg) | |
| self.vx0 = velocity * cos(theta) | |
| self.vy0 = velocity * sin(theta) | |
| self.x0 = x0 | |
| self.y0 = y0 | |
| self.x = x | |
| self.g = g | |
| self.noise = noise | |
| def position(self, t): | |
| """ returns (x,y) tuple of ball position at time t""" | |
| self.x = self.vx0*t + self.x0 | |
| self.y = -0.5*self.g*t**2 + self.vy0*t + self.y0 | |
| return (self.x +random.randn()*self.noise[0], self.y +random.randn()*self.noise[1]) | |
| class BallEuler(object): | |
| def __init__(self, y=100., vel=10., omega=0): | |
| self.x = 0. | |
| self.y = y | |
| omega = radians(omega) | |
| self.vel = vel*np.cos(omega) | |
| self.y_vel = vel*np.sin(omega) | |
| def step (self, dt): | |
| g = -9.8 | |
| self.x += self.vel*dt | |
| self.y += self.y_vel*dt | |
| self.y_vel += g*dt | |
| #print self.x, self.y | |
| def rk4(y, x, dx, f): | |
| """computes 4th order Runge-Kutta for dy/dx. | |
| y is the initial value for y | |
| x is the initial value for x | |
| dx is the difference in x (e.g. the time step) | |
| f is a callable function (y, x) that you supply to compute dy/dx for | |
| the specified values. | |
| """ | |
| k1 = dx * f(y, x) | |
| k2 = dx * f(y + 0.5*k1, x + 0.5*dx) | |
| k3 = dx * f(y + 0.5*k2, x + 0.5*dx) | |
| k4 = dx * f(y + k3, x + dx) | |
| return y + (k1 + 2*k2 + 2*k3 + k4) / 6. | |
| def fx(x,t): | |
| return fx.vel | |
| def fy(y,t): | |
| return fy.vel - 9.8*t | |
| class BallRungeKutta(object): | |
| def __init__(self, x=0, y=100., vel=10., omega = 0.0): | |
| self.x = x | |
| self.y = y | |
| self.t = 0 | |
| omega = math.radians(omega) | |
| fx.vel = math.cos(omega) * vel | |
| fy.vel = math.sin(omega) * vel | |
| def step (self, dt): | |
| self.x = rk4 (self.x, self.t, dt, fx) | |
| self.y = rk4 (self.y, self.t, dt, fy) | |
| self.t += dt | |
| print(fx.vel) | |
| return (self.x, self.y) | |
| def ball_scipy(y0, vel, omega, dt): | |
| vel_y = math.sin(math.radians(omega)) * vel | |
| def f(t,y): | |
| return vel_y-9.8*t | |
| solver = ode(f).set_integrator('dopri5') | |
| solver.set_initial_value(y0) | |
| ys = [y0] | |
| while brk.y >= 0: | |
| t += dt | |
| brk.step (dt) | |
| ys.append(solver.integrate(t)) | |
| def RK4(f): | |
| return lambda t, y, dt: ( | |
| lambda dy1: ( | |
| lambda dy2: ( | |
| lambda dy3: ( | |
| lambda dy4: (dy1 + 2*dy2 + 2*dy3 + dy4)/6 | |
| )( dt * f( t + dt , y + dy3 ) ) | |
| )( dt * f( t + dt/2, y + dy2/2 ) ) | |
| )( dt * f( t + dt/2, y + dy1/2 ) ) | |
| )( dt * f( t , y ) ) | |
| def theory(t): return (t**2 + 4)**2 /16 | |
| from math import sqrt | |
| dy = RK4(lambda t, y: t*sqrt(y)) | |
| t, y, dt = 0., 1., .1 | |
| while t <= 10: | |
| if abs(round(t) - t) < 1e-5: | |
| print("y(%2.1f)\t= %4.6f \t error: %4.6g" % (t, y, abs(y - theory(t)))) | |
| t, y = t + dt, y + dy(t, y, dt) | |
| t = 0. | |
| y=1. | |
| def test(y, t): | |
| return t*sqrt(y) | |
| while t <= 10: | |
| if abs(round(t) - t) < 1e-5: | |
| print("y(%2.1f)\t= %4.6f \t error: %4.6g" % (t, y, abs(y - theory(t)))) | |
| y = rk4(y, t, dt, test) | |
| t += dt | |
| if __name__ == "__main__": | |
| 1/0 | |
| dt = 1./30 | |
| y0 = 15. | |
| vel = 100. | |
| omega = 30. | |
| vel_y = math.sin(math.radians(omega)) * vel | |
| def f(t,y): | |
| return vel_y-9.8*t | |
| be = BallEuler (y=y0, vel=vel,omega=omega) | |
| #be = BallTrajectory2D (x0=0, y0=y0, velocity=vel, theta_deg = omega) | |
| ball_rk = BallRungeKutta (y=y0, vel=vel, omega=omega) | |
| while be.y >= 0: | |
| be.step (dt) | |
| ball_rk.step(dt) | |
| print (ball_rk.y - be.y) | |
| ''' | |
| p1 = plt.scatter (be.x, be.y, color='red') | |
| p2 = plt.scatter (ball_rk.x, ball_rk.y, color='blue', marker='v') | |
| plt.legend([p1,p2], ['euler', 'runge kutta']) | |
| ''' |
Xet Storage Details
- Size:
- 4.34 kB
- Xet hash:
- d5cdd8117e5253212424bdfd4b619043a75d3e09b0cf86e88e86bb86ea9857b7
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.