Created
April 28, 2024 04:05
-
-
Save e96031413/fed388c5bb2c31b040dfae195a4b6825 to your computer and use it in GitHub Desktop.
Backtesting TW stock with pandas, backtesting, talib, and FinMind
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from backtesting import Backtest, Strategy | |
from backtesting.lib import crossover | |
from FinMind.data import DataLoader | |
import pandas as pd | |
import talib | |
from talib import abstract | |
## 取得資料 | |
dl = DataLoader() | |
df = dl.taiwan_stock_daily(stock_id='2330', start_date='2008-01-01', end_date='2023-1-1') | |
## 整理資料格式 | |
df = df.rename(columns={"date": "Date"}) | |
df.set_index("Date" , inplace=True) | |
df = df.set_index(pd.DatetimeIndex(pd.to_datetime(df.index))) | |
## backtesting.py 格式 | |
df1 = df.rename(columns={"open": "Open", "max": "High", "min": "Low", "close": "Close", "Trading_Volume": "Volume"}) | |
## ta-lib 格式 | |
df2 = df.rename(columns={"max": "high", "min": "low", "Trading_Volume": "Volume"}) | |
## 取得 KD 值 | |
df_kd = abstract.STOCH(df2,fastk_period=9, slowk_period=3,slowd_period=3) | |
## 合併資料 | |
df1 = pd.merge(df1, df_kd, on="Date") | |
""" | |
KD 策略(K<20買;K>80賣) | |
""" | |
class KdCross(Strategy): | |
def init(self): | |
super().init() | |
def next(self): | |
if crossover(20, self.data.slowk): ## K<20 買進 | |
self.buy() | |
elif crossover(self.data.slowk, 80): ## K>80 平倉 | |
self.position.close() | |
bt = Backtest(df1, KdCross, cash=10000, commission=0.001798) ## 交易成本 0.1798% | |
output = bt.run() | |
print(output) | |
bt.plot() | |
""" | |
跌破季線買進;K>80賣出 | |
Strategy: 跌破60日均線買進, K>80賣出 | |
""" | |
# class PriceBelowMAandKDJ(Strategy): | |
# def init(self): | |
# super().init() | |
# self.ma_60 = self.I(talib.MA, self.data.Close, timeperiod=60) # 60-day moving average | |
# def next(self): | |
# if self.data.Close < self.ma_60: # Price falls below 60-day MA | |
# self.buy() | |
# elif self.data.slowk > 80: # KDJ > 80 | |
# self.position.close() | |
# bt = Backtest(df1, PriceBelowMAandKDJ, cash=10000, commission=0.001798) # 交易成本 0.1798% | |
# output = bt.run() | |
# print(output) | |
# bt.plot() | |
""" | |
跌破月線的兩個標準差買進;收盤價大於5日線的兩個標準差平倉 | |
""" | |
## Calculate 20-day mean and standard deviation | |
# df1['5_Day_MA'] = df1['Close'].rolling(window=5).mean() | |
# df1['5_Day_STD'] = df1['Close'].rolling(window=5).std() | |
# df1['20_Day_MA'] = df1['Close'].rolling(window=20).mean() | |
# df1['20_Day_STD'] = df1['Close'].rolling(window=20).std() | |
# class MeanReversionStrategy(Strategy): | |
# def init(self): | |
# super().init() | |
# def next(self): | |
# if self.data.Close < self.data['20_Day_MA']: | |
# self.buy() | |
# elif self.data.Close > self.data['5_Day_MA']: | |
# self.position.close() | |
# bt = Backtest(df1, MeanReversionStrategy, cash=10000, commission=0.001798) # 交易成本 0.1798% | |
# output = bt.run() | |
# print(output) | |
# bt.plot() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment