{ "metadata": { "name": "", "signature": "sha256:c5784c581ec769f2c12604f733412de04fb2880f6083803d744b7fda6d7e2f74" }, "nbformat": 3, "nbformat_minor": 0, "worksheets": [ { "cells": [ { "cell_type": "code", "collapsed": false, "input": [ "from IPython.core.display import HTML\n", "\n", "with open('creative_commons.txt', 'r') as f:\n", " html = f.read()\n", " \n", "name = '2014-02-17-chap2_coriolis_part2'\n", "\n", "html = \"\"\"\n", "\n", "

This post was written as an IPython notebook. It is available for\n", "download or as a static\n", "html.

\n", "

\n", "%s \"\"\" % (name, name, html)\n", "\n", "%matplotlib inline\n", "from matplotlib import style\n", "style.use('ggplot')" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 1 }, { "cell_type": "markdown", "metadata": {}, "source": [ "Second part of the chapter on Coriolis from\n", "[Introduction to Geophysical Fluid Dynamics, 2nd Edition](http://store.elsevier.com/product.jsp?isbn=9780120887590)\n", "\n", "Here I implemented mfiles `parabolic.m` (script that calls the animation) and `coriolisanim.m` (a function for the animation)\n", "\n", "The animation shows the trajectory of a particle on a parapoloid in absolute axes and the imprint of the trajectory on the rotating platform." ] }, { "cell_type": "code", "collapsed": false, "input": [ "import numpy as np\n", "import matplotlib.pyplot as plt\n", "from matplotlib import animation\n", "from JSAnimation import IPython_display" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 2 }, { "cell_type": "markdown", "metadata": {}, "source": [ "Other Examples (Figure 2.8):\n", "\n", "- $\\alpha$, $\\beta$, X0 = 0, 0, 5 $\\rightarrow$ part a.\n", "- $\\alpha$, $\\beta$, X0 = 1, 0, 5 $\\rightarrow$ part b.\n", "- $\\alpha$, $\\beta$, X0 = -1, 0, 5 $\\rightarrow$ part c." ] }, { "cell_type": "code", "collapsed": false, "input": [ "n = 101 # Number of time steps to show a full period.\n", "frames = n // 1 + 1 # Last time step (to show only half (quarter) a period divide by 2 (4)).\n", "alpha = 1.2 # Scaled azimuthal initial velocity V_0/(X_0 Omega).\n", "beta = 0.9 # Scaled radial initial velocity U_0/(X_0 Omega).\n", "X0 = 3 # Initial distance (less then 10 for plotting reasons)" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 3 }, { "cell_type": "code", "collapsed": false, "input": [ "def coriolisanim(n, frames, alpha, beta, X0):\n", " \"\"\"Function that shows the trajectory of a particle\n", " on a parapoloid in absolute axes and the imprint of\n", " the trajectory on the rotating platform.\"\"\"\n", "\n", " twopi = 2 * np.pi\n", " pio2 = np.pi / 2\n", "\n", " # Non-animate.\n", " k = np.arange(1, 102)\n", " xc = 10 * np.cos(k * twopi / 100)\n", " yc = 10 * np.sin(k * twopi / 100)\n", " XAA, YAA, xt, yt = [], [], [], []\n", "\n", " fig = plt.figure(figsize=(6, 6))\n", " ax = plt.axes(xlim=(-12, 12), ylim=(-12, 12))\n", " ax.plot([10.5, 12], [0, 0], color='grey', linestyle='-')\n", " ax.plot([0, 0], [10.5, 12], color='grey')\n", " ax.plot(xc, yc, color='black')\n", " ax.set_axis_off()\n", "\n", " # Animated.\n", " l1, = ax.plot([], [], color='grey', linestyle='-')\n", " p1, = ax.plot([], [], linestyle='none', marker='o', mfc='black', mec='white')\n", " l2, = ax.plot([], [], color='grey', linestyle='-')\n", " l3, = ax.plot([], [], linestyle='none', marker='.', mfc='green', mec='white')\n", " l4, = ax.plot([], [], linestyle='none', marker='o', mfc='green', mec='red')\n", " l5, = ax.plot([], [], color='red', linestyle='-')\n", "\n", " l1.set_data([], [])\n", " l2.set_data([], [])\n", " l3.set_data([], [])\n", " l4.set_data([], [])\n", " l5.set_data([], [])\n", " p1.set_data([], [])\n", "\n", " def init():\n", " return l1, l2, l3, l4, l5, p1\n", "\n", " def animate(j):\n", " ot = j * twopi / n # omega t\n", " dot = twopi / n # omega delta t\n", " # Four line segments to see rotation of plane (two segments fixed, two\n", " # segments attached to rotating table.\n", " x1 = 7 * np.cos(j * twopi / n), 10 * np.cos(j * twopi / n)\n", " z1 = 7 * np.sin(j * twopi / n), 10 * np.sin(j * twopi / n)\n", " x2 = 10 * np.cos(j * twopi / n + pio2), 7 * np.cos(j * twopi / n + pio2)\n", " z2 = 10 * np.sin(j * twopi / n + pio2), 7 * np.sin(j * twopi / n + pio2)\n", "\n", " # XXA and YAA solution in absolute axes as a function of initial\n", " # conditions.\n", " XA = X0 * np.cos(ot) + beta * X0 * np.sin(ot)\n", " YA = alpha * X0 * np.sin(ot)\n", " # Storage of trajectory in absolute axes.\n", " XAA.append(XA)\n", " YAA.append(YA)\n", " # Rotation of trajectory inprint on rotating axis.\n", " for i in range(0, j):\n", " xn = xt[i] * np.cos(dot) - yt[i] * np.sin(dot)\n", " yn = xt[i] * np.sin(dot) + yt[i] * np.cos(dot)\n", " xt[i] = xn\n", " yt[i] = yn\n", " xt.append(XA)\n", " yt.append(YA)\n", " # Adding of new point to the trajectory.\n", " l1.set_data(x1, z1)\n", " l2.set_data(x2, z2)\n", " l3.set_data(xt, yt)\n", " l4.set_data(XA, YA)\n", " l5.set_data(XAA, YAA)\n", " p1.set_data(x1[1], z1[1])\n", " return l1, l2, l3, l4, l5, p1\n", "\n", " return animation.FuncAnimation(fig, animate, init_func=init,\n", " frames=frames, interval=100)\n", "\n", "coriolisanim(n=n, frames=frames, alpha=alpha, beta=beta, X0=X0)" ], "language": "python", "metadata": {}, "outputs": [ { "html": [ "\n", "\n", "\n", "
\n", " \n", "
\n", " \n", "
\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
\n", " Once \n", " Loop \n", " Reflect \n", "
\n", "
\n", "\n", "\n", "\n" ], "metadata": {}, "output_type": "pyout", "prompt_number": 4, "text": [ "" ] } ], "prompt_number": 4 }, { "cell_type": "code", "collapsed": false, "input": [ "HTML(html)" ], "language": "python", "metadata": {}, "outputs": [ { "html": [ "\n", "\n", "

This post was written as an IPython notebook. It is available for\n", "download or as a static\n", "html.

\n", "

\n", "
python4oceanographers by Filipe Fernandes is\n", "licensed under a Creative Commons\n", "Attribution-ShareAlike 4.0 International License.
Based on a work at https://ocefpaf.github.io/.\n", " " ], "metadata": {}, "output_type": "pyout", "prompt_number": 5, "text": [ "" ] } ], "prompt_number": 5 } ], "metadata": {} } ] }