懶惰之最|GitHub 實測

每天留一份股價紀錄:用 ta 把公開價格表加上平均欄

2026-10-29|專案:bukosabino/ta|金融工具區|Markdown 版

📌 數據僅限本工具現階段參考用。本文只示範工具怎麼安裝、設定、執行,不是投資建議,也不推薦任何股票。

重點摘要

  • ta 0.11.0 在 Python 3.12.14 以證交所2026-09-01至2026-10-28公開資料37筆產出CSV。
  • 輸出有Date、Close、SMA5、SMA20、RSI14共5欄,其中3個是新增計算欄位。
  • fillna=False時,三個計算欄開頭分別保留4、19、13格空白。
  • 本輪沿用成功實錄,另以標準函式獨立核對185個來源值及75個計算值,全部通過。
  • 結論: 固定設定可把37筆公開收盤資料輸出成含三個計算欄位的CSV。
  • 適合: 收盤後想留每日價格與近期平均紀錄,且可依教學執行Python的人
  • 不適合: 需要點選式網站介面的人
實測項目 結果
公開資料日期 2026-09-01至2026-10-28
資料列數 37
新增計算欄位 3
來源數值核對 185個相同
SMA20初期空白 19格

收盤後想留一份紀錄,日後打開就能同時查到當天價格與最近幾天的平均。從證交所下載的原始表有每天的價格,卻不會附上自己想要的五日平均、二十日平均;若用試算表補公式,每天增加資料時還得確認新的一列也有算到。這才是本次使用 ta 的起點:把固定計算步驟保存,之後換資料再產表。

這是提供給會執行 Python、想保留固定資料整理步驟的人的方法。ta 是計算套件,沒有自己的試算表視窗;影片中的深藍表格是本片自製的 CSV 檢視與金融排版,讀取真實輸出,並非套件原生介面。開頭「每天留紀錄」是使用情境說明,不是使用者訪談或已執行的每日排程。本次修訂沿用 10 月 29 日既有核心實測和錄影,沒有把重剪說成重跑。

下載

來源是 bukosabino/ta。受測版本 0.11.0,原始碼提交 a890410710a6e483c9ba08da7f3dd5089e4b9dff,使用 Python 3.12.14,主要依賴 pandas、NumPy;下載公開資料另用 requests。測試設備為 Mac mini M4 Pro(12 核、64GB)。

python3 -m venv .venv
source .venv/bin/activate
python -m pip install ta==0.11.0 pandas==3.1.0 numpy==2.5.4 requests==2.34.2

設定

本文示範資料是證交所公開資料,資料日期為 2026-09-01 至 2026-10-28,共 37 筆日資料。 10 月 28 日是本次查詢時最近一個已完成的交易日。資料不是套件自己抓的:本次腳本呼叫證交所 STOCK_DAY 公開端點,分兩個月份取得 JSON,再交給 ta。沒有使用帳戶、券商登入或金鑰。2330 只是示範輸入代號。

要成功讀取,先把民國日期轉成西元,按日期排序,將價格與成交量的千分逗號去掉。這些整理步驟放在下面的完整腳本。原始檔保留供核對,不用手動補上不存在的交易日。

輸入的證交所收盤資料

跑起來

把下面存為 demo.py,再執行。時間範圍刻意固定,方便重現;改作日常工作時,請同步修改月份和截止日期,並確認已取得收盤後的完整資料。

python demo.py
import json,csv,time,sys
from pathlib import Path
import requests,pandas as pd,numpy as np
from ta.trend import SMAIndicator
from ta.momentum import RSIIndicator
rows=[]
for month in ['20260901','20261001']:
 r=requests.get('https://www.twse.com.tw/exchangeReport/STOCK_DAY',params={'response':'json','date':month,'stockNo':'2330'},timeout=40)
 r.raise_for_status();raw=r.json();assert raw['stat']=='OK',raw.get('stat')
 Path('twse-'+month+'.json').write_text(json.dumps(raw,ensure_ascii=False))
 for a in raw['data']:
  y,m,d=map(int,a[0].split('/'));date=f'{y+1911}-{m:02}-{d:02}'
  if date<='2026-10-28':rows.append([date,*[float(a[i].replace(',','')) for i in [3,4,5,6,1]]])
 time.sleep(2)
df=pd.DataFrame(rows,columns=['Date','Open','High','Low','Close','Volume']).drop_duplicates('Date').sort_values('Date')
assert df.iloc[-1].Date=='2026-10-28','latest completed trading day missing'
assert not df.isna().any().any()
df.to_csv('input.csv',index=False)
t=time.perf_counter();out=df[['Date','Close']].copy()
out['SMA5']=SMAIndicator(df.Close,window=5,fillna=False).sma_indicator()
out['SMA20']=SMAIndicator(df.Close,window=20,fillna=False).sma_indicator()
out['RSI14']=RSIIndicator(df.Close,window=14,fillna=False).rsi()
assert out.SMA5.isna().sum()==4
assert out.SMA20.isna().sum()==19
assert out.RSI14.isna().sum()==13
assert np.allclose(out.SMA5.dropna(),df.Close.rolling(5).mean().dropna())
assert np.allclose(out.SMA20.dropna(),df.Close.rolling(20).mean().dropna())
out.to_csv('indicators.csv',index=False,float_format='%.4f')
print('TWSE PUBLIC DATA | 2330 demonstration input')
print(f'DATA {df.Date.iloc[0]} to {df.Date.iloc[-1]} | {len(df)} daily rows | missing input 0')
print('OUTPUT indicators.csv | columns: Date, Close, SMA5, SMA20, RSI14')
print('WARMUP blank cells: SMA5=4, SMA20=19, RSI14=13 | fillna=False')
print('SMA5 and SMA20 independently checked with pandas rolling: PASS')
print(f'Calculation and CSV write: {time.perf_counter()-t:.4f} seconds')
print(out.tail(3).to_string(index=False))
print('Python',sys.version.split()[0])

執行後會留下兩個月的原始 JSON、input.csv 和 indicators.csv。後者依序有 Date、Close、SMA5、SMA20、RSI14 五欄,保留日期與收盤,新增三個計算欄位。這次計算到 CSV 寫出約 0.0071 秒;不含資料下載和安裝,不能拿來當端到端時間。

實測項目 結果
輸入 37 列,日期與五個數值欄
輸出 37 列、5 欄,新增 3 個計算欄位
開頭保留空白 SMA5 為 4 格、SMA20 為 19 格、RSI14 為 13 格
原始數值核對 185 個來源數值與 CSV 相同
獨立重算 兩種平均及 RSI 已逐格核對至 CSV 的四位小數容許差

實際輸出的計算欄位與暖機空格

常見問題

前面為什麼空白? 本次明確指定 fillna=False。二十日平均要累積二十筆輸入,所以前十九格不會有值;這是這次設定的結果。CSV 裡是空欄位,影片檢視器以長橫線顯示,沒有把它補成零。原始輸入數值沒有缺漏,與計算初期的空格是兩回事。

下載不到怎麼辦? 腳本會檢查 HTTP 回應及 stat;沒有回傳 OK 就停止,不把空資料繼續算下去。先檢查查詢月份與官方服務狀態,避免密集重複請求。本次抓取成功,沒有宣稱重現過官方服務中斷。

能直接點兩下操作嗎? 這是 Python 套件,讀者需要能建立環境及執行腳本。適合固定整理價格資料、希望保存計算步驟的人;只想開網站看現成表格的人,不適合直接拿它當網站使用。這次驗證上述三欄及 CSV 輸出,其他指標、即時更新及長期排程沒有驗證。

每天需要這份紀錄時,可以保留設定;下次先核對新資料,再重新產表。這是使用建議,本次沒有測試每日自動更新。它的實際用途是把重複計算留在程式裡,讓輸出格式保持一致;本文不解讀示範數值。原測試有成功收據;本輪另將 185 個來源數值和 75 個計算值以標準函式獨立核對,四位小數容許差 0.00006,全部通過。完整資料收據與腳本隨本次成品保留。

專案:bukosabino/ta;授權:MIT。官方 API 說明:ta 文件。資料:證交所個股日成交資訊。

測試設備:Mac mini M4 Pro(12 核、64GB)。內容依實際執行結果撰寫,數據為撰寫當時的實測值。

← 金融工具區|所有實測