{ "cells": [ { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#Shuttlecocks and the Akaike Information Criterion\n", "#A worksheet to help explore the project in Section 3.5.4.\n", "\n", "#The Data: First, the data for the shuttlecock's fall, in time (seconds)/distance (meters) pairs:\n", "shuttledata = [[0, 0], [0.347, 0.61], [0.47, 1.00], [0.519, 1.22], [0.582, 1.52], [0.650, 1.83], [0.674, 2.00], \n", " [0.717, 2.13], [0.766, 2.44], [0.823, 2.74], [0.870, 3.00], [1.031, 4.00], [1.193, 5.00], \n", " [1.354, 6.00], [1.501, 7.00], [1.726, 8.50], [1.873, 9.50]];\n", "N = len(shuttledata);" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#A plot\n", "plt1 = scatter_plot(shuttledata,facecolor='red');\n", "show(plt1)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#The Model: We might posit a model of the form v'(t) = g (no air resistance) and consider g as an unknown,\n", "#to be estimated. Then the governing ODE is (from equation (3.68) in the text)\n", "var('g t');\n", "v = function('v')(t)\n", "de = diff(v,t) == g\n", "vsol(t) = desolve(de,v,[0,0],t); #Solve with v(0) = 0." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#Integrate to obtain the position in terms of t and k, taking x(0) = 0.\n", "var('tau');\n", "x(t,g) = integral(vsol(tau),tau,0,t);" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#Estimating Parameters: Form a sum of squares\n", "SS = function('SS')(g);\n", "SS(g) = add((x(shuttledata[i][0])-shuttledata[i][1])^2 for i in range(N));" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#A quick plot of SS(g)\n", "plot(SS(g), (g,0,15)).show()" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#We can solve by setting dSS/dg = 0 and solving for g.\n", "criteqn = diff(SS,g) == 0;\n", "gbest = find_root(criteqn,5,15) #Look between 5 and 15." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#The residual is\n", "SS(gbest)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#Plot the function x(t) with this best choice for g.\n", "plt2 = plot(x(t,gbest), t, 0, 1.873);\n", "pp = plt1 + plt2;\n", "show(plt1+plt2)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "#An alternative is to use Sage's \"model fitting\" ability, to adjust\n", "#k in the function x(t,g) to best fit the data.\n", "model(t) = x(t,g); #Specify the model to be fit, with \"t\" as the independent variable\n", "sol = find_fit(shuttledata,model,parameters=[g]) #Fit the model by adjusting k and b\n", "bestx(t) = model(g=sol[0].rhs()) #Define the best fit function of the form in \"model\"" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "bestx(t)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] } ], "metadata": { "kernelspec": { "display_name": "SageMath 9.2", "language": "sage", "name": "sagemath" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.7.7" } }, "nbformat": 4, "nbformat_minor": 4 }