点Pを作ろう!
- guan satai
- 2020年6月27日
- 読了時間: 2分
中学校のころから数学の試験でよく「点P」が登場しなかっただろうか?図形の上やグラフの上を動きやがる「点P」には苦しめられた経験が誰しもあるでしょう。今回はにっくき「点P」を再現しよう、という記事になります。
使用するのはpythonとそのライブラリの一つplotlyなどです。plotlyはExcelではできないようなきれいなグラフを作ってくれる便利な機能が付いています。今回は放射崩壊のようなdn/dt=-ktで表される簡単な微分方程式をルンゲクッタ法で数値解を求め、それを基にグラフを作成していきましょう。ルンゲクッタ法に関しては他のサイトで詳しく述べているので借用させていただきます。(http://shimaphoto03.com/science/rk-method/)k=0.05として解いていきましょう。この値には特に意味はないのであしからず。
まずは必要なライブラリをimportしましょう。道具箱から道具を取り出すイメージです。
その次に別に用意した適当なxの値を与えましょう。今回のプログラムでいうところのaの行列のことで、0から1まで0.01刻みでxの値を与えてあります。その後、初期値を100としてルンゲクッタ法を実行します。この詳しい中身は先ほど挙げたサイトで確認してください。計算が終わったらグラフ化する前準備としての表作成をします。表を表示していないのでそのように見えませんが、実は時間t、個数N、k1、k2、k3、k4を使った表が作成されています。ここからようやくグラフの表示と相成るわけですが、説明が難しくなる上、私の浅学がばれてしまうのであまり注釈は入れません。詳しくはplotlyのHPを見てください。(https://plotly.com/python/animations/)
さて、これでどのようなグラフができたか見てみましょう。
どうでしょうか。青い曲線の上を赤い点が動いている様が見えると思います。これが多くの学生を苦しめる「点P」なのです!
以下、今回のプログラムです。実行してみたい方は各ライブラリが使える環境で実行してみてください。
import pandas as pd
import numpy as np
%matplotlib inline
from plotly import __version__
from plotly.offline import download_plotlyjs, init_notebook_mode, plot, iplot
import cufflinks as cf
import chart_studio.plotly as py
import plotly.graph_objects as go
#calculation with Runge–Kutta method
N0=100
k=0.05
N_list=[N0]
k1=[]
k2=[]
k3=[]
k4=[]
a=np.arange(0,1,0.01)
column=['time']
for i in range(len(a-1)):
k1.append(-k*N_list[i])
k2.append(-k*(N_list[i]+k1[i]/2))
k3.append(-k*(N_list[i]+k2[i]/2))
k4.append(-k*(N_list[i]+k3[i]))
N_list.append(N_list[i]+(k1[i]+2*k2[i]+2*k3[i]+k4[i])/6)
# Making the table of the result of culculation
k_list=[k1,k2,k3,k4]
karr=np.array(k_list)
dfk=pd.DataFrame(data=karr.T,columns=['k1','k2','k3','k4'])
dfN=pd.DataFrame(data=N_list,columns=['N'])
df2=pd.concat([df,dfN,dfk],axis=1)
N = len(a)
xx = df2['time']
yy = df2['N']
# Create figure
fig = go.Figure(
data=[go.Scatter(x=df2['time'], y=df2['N'],
mode="lines",
line=dict(width=2, color="blue")),
go.Scatter(x=df2['time'], y=df2['N'],
mode="lines",
line=dict(width=2, color="blue"))],
layout=go.Layout(
xaxis=dict(range=[0, 1], autorange=False, zeroline=False),
yaxis=dict(range=[0, 100], autorange=False, zeroline=False),
title_text="Kinematic Generation of a Planar Curve", hovermode="closest",
updatemenus=[dict(type="buttons",
buttons=[dict(label="Play",
method="animate",
args=[None])])]),
frames=[go.Frame(
data=[go.Scatter(
x=[xx[k]],
y=[yy[k]],
mode="markers",
marker=dict(color="red", size=10))])
for k in range(N)]
)
fig.show()
Commenti