熱門文章

2019年12月31日 星期二

木棍轉動落下所需時間

作者:王一哲
日期:2019/12/1




前言


我最近在 YouTube 上看到李永樂老師的一部影片:家長輔導小學生作業崩潰:抽出我“40米長大砍刀”,你有幾秒逃生時間?,李老師在影片中很正經地用物理理論,計算40米長大砍刀轉動落下所需時間,這樣一本正經地講解奇怪的東西也挺有趣的。以下用兩種方法計算類似的問題,但是為了使情境稍微正常一點,我將物體改為長度為$L = 1 ~\mathrm{m}$、質量均勻分布的木棍,下端立於水平桌面上,木棍與桌面的夾角$\theta$原為89°,並假設落下過程中木棍不會滑動。



理論計算


假設木棍的質量為$m$且質量均勻分布,長度$L = 1 ~\mathrm{m}$,下端立於水平桌面上,木棍與桌面的夾角原為$\theta_0 = 89^{\circ}$,受到重力作用由靜止開始落下,重力加速度$g = 9.8~\mathrm{m/s^2}$

若以下端為轉軸,則轉動慣量
$$I = \frac{1}{3}mL^2$$

重力產生的力矩
$$\tau = \frac{1}{2}mgL \cos \theta$$

角加速度
$$\alpha = \frac{\tau}{I} = \frac{3g \cos \theta}{2L}$$

由於轉動動能
$$K = \frac{1}{2}I \omega^2$$

當木棍與水平方向夾角為$\theta$時,角速度為$\omega$,由力學能守恆可得
$$\frac{1}{2} \cdot \frac{1}{3}mL^2 \cdot \omega^2 + \frac{1}{2}mgL \sin \theta = 0 + \frac{1}{2}mgL \sin \theta_0$$

$$\omega = \sqrt{\frac{3g(\sin \theta_0 - \sin \theta)}{L}}$$

假設木棍轉動一個很小的角位移$d \theta$,由於$\omega$與$d \theta$反方向,所需時間為
$$dt = -\frac{d \theta}{\omega}$$

當角度由$\theta_0$變為$\theta$時,可以算出經過的時間
$$t = \int_0^t dt = \int_{0}^{\theta_0} \frac{d \theta}{\omega} = \sqrt{\frac{L}{3g}}\int_{0}^{\theta_0} (\sin \theta_0 - \sin \theta)^{-\frac{1}{2}} d \theta$$

無法得到解析解,可以求數值解。利用SymPy計算角度$\theta$由$89^{\circ}$開始,變為$88^{\circ}$、$87^{\circ}$、……、$0^{\circ}$所經過的時間,程式碼寫法如下

2019年12月23日 星期一

U 形物體與木塊系統的動量守恆

作者:王一哲
日期:2019/12/23




題目


在水平光滑桌面上有一個質量為 1.8 kg 的 U 形物體,左、右兩側各連接一條原長為 0.5 m、彈性常數為 5.0 N/m 的理想彈簧,將一個質量為 0.2 kg 的木塊放在水平底面上,將右側的彈簧向右壓縮 0.2 m,整個系統原為靜止,假設摩擦力可以忽略,將木塊釋放後整個系統會如何運動?


模擬動畫畫面截圖



理論推導


由於右側彈簧原來被壓縮,右側彈簧的回復力會將木塊往左推、將 U 形物體往右推;當木塊開始壓縮左側的彈簧時,左側彈簧的回復力會將木塊往右推、將 U 形物體往左推;由於整個系統所受外力合為0,系統動量守恆,質心速度為0。



2019年12月20日 星期五

Matplotlib 繪圖技巧:移動的點

作者:王一哲
日期:2019/12/20




前言


在這篇文章中,我利用 Matplotlib 繪製一個隨著 sin 函數移動的點,由於圖片中的物件比較簡單,算是上一篇文章〈Matplotlib 繪圖技巧:水波干涉動畫〉的前置作業。


使用Matplotlib產生的動畫



2019年12月14日 星期六

小球與圓環碰撞

作者:王一哲
日期:2019/12/14




題目


在水平光滑桌面上有一個質量為$m_1$的小球及一個質量為$m_2$的圓環,小球放置於圓環的圓心處。若兩者原為靜止,用手撥動小球,使小球以初速度$v_1$向右移動,小球與圓環之間為彈性碰撞,請問兩者會如何運動?


模擬動畫畫面截圖



理論推導


當小球開始運動之後,小球與圓環系統所受外力合為0,因此系統動量守恆,質心速度為定值、方向向右。小球向右移動,第1次撞擊圓環時使圓環開始向右移動,小球的速度變慢或反向移動;接下來小球撞擊圓環左側,使圓環減速、小球向右移動;不斷重複這個過程,整個系統向右移動。


2019年12月13日 星期五

解決 Linux Mint 上 HackMD 網頁等寬字體問題

日期:2019/12/13
作者:王一哲




我在 Linux Mint 19.1 Cinnamon 上使用 Chrome 瀏覧器開啟 HackMD 網站時,程式碼的部分沒有辦法使用等寬字體顯示,這樣很難看清楚縮排的格數,今天剛好遇到一個高手學生幫我解決了這個問題。




無法使用等寬字體顯示程式碼



先在程式碼區段按滑鼠右鍵開啟快速選單,點選最下方的檢查

開啟快速選單


2019年12月12日 星期四

Matplotlib 繪圖技巧:水波干涉動畫

作者:王一哲
日期:2019/12/12




前言


以前在維基百科上看到用 MATLAB 繪製的兩個點波源水波干涉動畫,後來我參考網頁上的程式碼,試著用 Scilab 畫出一樣的動畫,甚至把它改成立體圖。但是我現在比較常用 Matplotlib 套件繪圖,也在網路上看過一些用 Matplotlib 繪製的 gif 檔,於是我花了一點時間研究一下繪製動畫的方法。


維基百科兩個點波源水波干涉動畫,圖片來源為 https://en.wikipedia.org/wiki/File:Two_sources_interference.gif




使用 Scilab 自行繪製的水波干涉動畫(2D版)




使用 Scilab 自行繪製的水波干涉動畫(3D版)


2019年12月6日 星期五

SciDAVis 教學 1:XY 散佈圖基本使用方法

作者:王一哲
日期:2019/12/4




SciDAVis 的全名為 Scientific Data Analysis and Visualization,照字面的意思可以翻譯為科學資料分析與視覺化工具,用來分析數據、作圖,而且它是一套自由軟體最新的版本為1.25,下載頁面在此(前往下載) 。類似的商業軟體為 OriginSigmaPlot,但是這兩套軟體的售價不便宜,都在萬元以上。雖然用 MicroSoft Excel 和 LibreOffice Calc 也能做到類似的效果,但是 SciDAVis 處理大量數據的效果更好,即使操作界面是沒有中文化,對高中生而言應該還在可接受的範圍內。




SciDAVis

安裝軟體


如果作業系統為 Windows,請選用 scidavis.1.25-win-dist.msi,下載後使用系統管理員身份執行安裝檔,接著不斷地按下一步就完成了。如果作業系統為 Linux,請選用 scidavis-1.25.tar.gz,下載後解壓縮,再依照資料夾中的檔案 "README.installer" 的指示編輯檔案及安裝。安裝完成後執行程式,畫面如下。


SciDAVis 畫面截圖


SciDAVis 教學 2:作圖技巧及化直

作者:王一哲
日期:2019/12/4




作圖原則


  1. 假設自變數為$x$、應變數為$y$,先畫出$y-x$關係圖,如果數據點看起來分布在一條斜直線上,利用線性迴歸畫出最接近直線,計算斜率、截距及其不準量;如果數據點看起來是分布在一條曲線上則進行步驟2。
  2. 計算 $\log x$、$\log y$,畫出$\log y - \log x$關係圖,如果數據點看起來分布在一條斜直線上,利用線性迴歸畫出最接近直線,計算斜率、截距及其不準量,其中斜率可以代表$x$、$y$取幾次方時兩者的關係為線性。假設$x$、$y$數學關係為
    $$y^m = kx^n$$
    $$m \log y = \log k + n \log x$$
    $$\log y = \frac{n}{m} \log x + \frac{\log k}{m}$$
    因此$\log y - \log x$關係圖的最接近直線斜率為$n/m$。
  3. 計算 $x^n$、$y^m$,畫出$y^m - x^n$關係圖,如果數據點看起來分布在一條斜直線上,利用線性迴歸畫出最接近直線,計算斜率、截距及其不準量。



自由落下時間與高度關係圖


假設小球原為靜止、離地面高度為$h$、受到重力作用開始落下,只考慮重力的作用,重力加速度$g = 9.8~\mathrm{m/s^2}$,小球在空中飛行時間為$t$、飛行時間不準量為$errt$,實驗數據如下

h(m),t(s),errt(s)
2,0.65,0.01
4,0.89,0.01
6,1.11,0.01
8,1.27,0.01
10,1.42,0.01
12,1.57,0.01
14,1.71,0.01
16,1.79,0.01
18,1.92,0.01
20,2.03,0.01



先畫出$t - h$關係圖,發現數據點應該是分布在一條曲線上,無法進行線性擬合。


t - h 關係圖


2019年12月2日 星期一

Streamplot 範例

作者:王一哲
日期:2019/12/2




前言


我為了寫〈均勻帶電圓環的電場〉找到了 matplotlib 官網上關於 streamplot 指令的範例,範例中利用 numpy 的指令直接產生繪圖資料,但是我需要從 csv 檔中讀取由 VPython 產生的資料,因此我需要改寫範例的程式碼。




streamplot 指令範例繪圖成果



2019年12月1日 星期日

均勻帶電圓環的電場

作者:王一哲
日期:2019/12/1




前言


這是一個選修物理上第6章靜電學的題目,但是題目只會問圓心處或是圓心上一段距離處的電場,因為這些位置才能利用對稱性計算電場量值,如果想計算其它位置的電場該怎麼辦?由於我們在 VPython 教學〈靜電力及簡諧〉程式 19-3 已經寫過類似的東西,應該可以從這支程式開始修改。



用 VPython 計算空間中各處的電場


GlowScript 版本
from vpython import *

"""
 1. 參數設定, 設定變數及初始值
"""
Q, R, N = 2E-11, 1, 100  # 帶電圓環總電量, 半徑, 分割數量
q, r = Q/N, 0.01*R       # 分割後小球電量, 半徑
L = 4.1*R                # 畫面寬度
ke = 8.988E9             # 靜電力常數
num = 100                # 將顯示的空間每邊切成 N 等份

"""
 2. 產生帶電球體類別, 回傳帶電球體產生的電場
"""
class Ball:
    def __init__(self, pos, radius, color, charge):
        self.pos = pos
        self.radius = radius
        self.color = color
        self.charge = charge
        self.ball = sphere(pos=self.pos, radius=self.radius, charge=self.charge, color=self.color)
    def electric(self, pos2):
        return ke*self.charge / mag2(pos2-self.pos) * norm(pos2-self.pos)

"""
 3. 畫面設定
"""
# 產生動畫視窗
scene = canvas(title="Electric Field (Circle)", width=600, height=600, x=0, y=0,               
               background=color.black, center=vec(0, 0, 0), range=L)

# 產生帶電圓環上計算電場用的小球
balls = [Ball(pos=vec(R*cos(i*2*pi/N), R*sin(i*2*pi/N), 0), radius=r, color=color.white, charge=q) for i in range(N)]

# 計算畫箭頭的位置
locations = []

# 直線, 儲存資料後用 plot 繪圖
'''
for i in range(num+1):
    locations.append(vec(L/num*i - L/2, 0, 0))
'''
# 平面, 儲存資料後用 streamplot 繪圖
for i in range(num+1):
    for j in range(num+1):
        locations.append(vec(L/num*i - L/2, L/num*j - L/2, 0))

# 立體, 展示用, 但是箭頭太多, 不容易看清楚
'''
for i in range(num+1):
    for j in range(num+1):
        for k in range(num+1):
            locations.append(vec(L/num*i - L/2, L/num*j - L/2, L/num*k - L/2))
'''

# 依序讀取串列 locations 的元素, 在對應的位置產生箭頭
fields = [arrow(pos=location, axis=vec(0, 0, 0), color=color.green) for location in locations]

with open("ElectricFieldCircleData.csv", "w", encoding="UTF-8") as file:
    file.write("x, y, E, Ex, Ey\n")
    
# 更新箭頭的長度及方向, 記錄電場強度最大值, 量值接近最大值偏紅色, 量值接近 0 偏綠色
fmax = 0
for field in fields:
    for ball in balls:
        field.axis += ball.electric(field.pos)
    with open("ElectricFieldCircleData.csv", "a", encoding="UTF-8") as file:
        file.write(str(field.pos.x) + "," + str(field.pos.y) + "," + str(field.axis.mag) + "," + str(field.axis.x) + "," + str(field.axis.y) + "\n")
    if(field.axis.mag >= fmax): fmax = field.axis.mag

for field in fields:
    field.color = vec(field.axis.mag/fmax, 1 - field.axis.mag/fmax, 0)