#!/usr/bin/env python # coding: utf-8 # # 畫出 個股/大盤 K線圖與成交量 # # Part 0: Import 套件 # In[1]: # 下載資料套件 import requests as r #資料處理套件 import pandas as pd import numpy as np import json from datetime import datetime, date # 畫圖套件 import plotly.graph_objects as go from plotly.subplots import make_subplots # # Part 1: 台股個股K線圖與成交量(成交股數) # ## 1.1 下載台股個股歷史走勢資料 - 成交股數 # - 股海小英雄youtube影片:[【Python 爬蟲】台股個股資料免費下載|選擇想要的個股資料!](https://youtu.be/_4CEymrQbV8) # - 資料來源:[證交所 個股日成交資訊](https://www.twse.com.tw/zh/page/trading/exchange/STOCK_DAY.html) # In[2]: def get_tw_stock_data(start_year, start_month, end_year, end_month, stock_code): start_date = str(date(start_year, start_month, 1)) end_date = str(date(end_year, end_month, 1)) month_list = pd.date_range(start_date, end_date, freq='MS').strftime("%Y%m%d").tolist() df = pd.DataFrame() for month in month_list: url = "https://www.twse.com.tw/exchangeReport/STOCK_DAY?response=json&date="+ month + "&stockNo=" + str(stock_code) res = r.get(url) stock_json = res.json() stock_df = pd.DataFrame.from_dict(stock_json['data']) df = df.append(stock_df, ignore_index = True) # 資料轉型 for col in [0, 1, 2, 3, 4, 5, 6, 8]: for row in range(df.shape[0]): # 把"日期"從字串(string)換成時間(datetime),並將民國年換成西元年 if col == 0: day = df.iloc[row,0].split('/') df.iloc[row, 0] = datetime(int(day[0]) + 1911, int(day[1]), int(day[2])) # 把"開盤價", "最高價", "最低價", "收盤價"帶有逗號的字串(string)換成浮點數(float) elif col != 0: df.iloc[row, col] = float(df.iloc[row,col].replace(',', '')) df.columns = ['日期', '成交股數', '成交金額', '開盤價', '最高價', '最低價', '收盤價', '漲跌價差', '成交筆數'] return df # In[3]: #下載台股台積電:2330 df = get_tw_stock_data(start_year = 2021, start_month = 9, end_year = 2021, end_month = 10, stock_code = 2330) df # ## 1.2 畫出個股K線圖與成交股數 # - 股海小英雄youtube影片:[【股市分析】用K線預測大盤趨勢](https://youtu.be/FX6YAyOdEaE) # In[4]: # 設定子圖 fig = make_subplots(rows = 2, cols = 1, shared_xaxes = True, vertical_spacing = 0.05, row_width=[0.2, 0.7]) # 畫K線圖 fig.add_trace(go.Candlestick(x = df['日期'], open = df['開盤價'], high = df['最高價'], low = df['最低價'], close = df['收盤價'], increasing_line_color = 'red', decreasing_line_color = 'green', name = 'K線圖'), row = 1, col = 1) # 畫成交量長條圖 fig.add_trace(go.Bar(x = df['日期'], y = df['成交股數'], showlegend = False, name = '成交股數'), row = 2, col = 1) # 設x軸標題 fig.update_xaxes(rangebreaks = [{ 'pattern': 'day of week', 'bounds': [6, 1]}]) fig.update_xaxes(title_text = "日期", row = 2, col = 1) # 設y軸標題 fig.update_yaxes(title_text = "股價", row = 1, col = 1) # 設圖標及圖長寬 fig.update_layout( title_text = "2021/09 - 2021/10 台積電(2330) K線圖", width = 800, height = 400 ) fig.update(layout_xaxis_rangeslider_visible = False) fig.show() # ## 1.3 畫出個股K線圖與成交股數,標上成交股數的顏色 # In[5]: df["成交量增減"] = df['成交股數'].diff() df # In[6]: df["成交量顏色"] = np.where(df["成交量增減"] >= 0, 'red', 'green') df # In[7]: # 第一筆資料沒有成交量增減,所以當收盤價>=開盤價標示紅色,收盤價<開盤價標示綠色 if df.iloc[0, 6] - df.iloc[0, 3] >= 0: df.iloc[0, 10] = 'red' else: df.iloc[0, 10] = 'green' # In[8]: df # In[9]: # 設定子圖 fig = make_subplots(rows = 2, cols = 1, shared_xaxes = True, vertical_spacing = 0.05, row_width=[0.2, 0.7]) # 畫K線圖 fig.add_trace(go.Candlestick(x = df['日期'], open = df['開盤價'], high = df['最高價'], low = df['最低價'], close = df['收盤價'], increasing_line_color = 'red', decreasing_line_color = 'green', name = 'K線圖'), row = 1, col = 1) # 畫成交量長條圖 fig.add_trace(go.Bar(x = df['日期'], y = df['成交股數'], showlegend = False, name = '成交股數', marker_color = df['成交量顏色']), row = 2, col = 1) # 設x軸標題 fig.update_xaxes(rangebreaks = [{ 'pattern': 'day of week', 'bounds': [6, 1]}]) fig.update_xaxes(title_text = "日期", row = 2, col = 1) # 設y軸標題 fig.update_yaxes(title_text = "股價", row = 1, col = 1) # 設圖標及圖長寬 fig.update_layout( title_text = "2021/09 - 2021/10 台積電(2330) K線圖", width = 800, height = 400 ) fig.update(layout_xaxis_rangeslider_visible = False) fig.show() # # Part 2: 大盤K線圖與成交量(成交金額) # ## 2.1 下載大盤指數歷史資料 # - 股海小英雄youtube影片 - 大盤開高低收價:[【Python 爬蟲】台股大盤資料免費下載|不必再到證交所的網站慢慢下載!](https://youtu.be/taiSnAeTs7Y) # In[10]: #下載大盤指數歷史資料 def get_stock_market_price(start_year, start_month, end_year, end_month): start_date = str(date(start_year, start_month, 1)) end_date = str(date(end_year, end_month, 1)) month_list = pd.date_range(start_date, end_date, freq='MS').strftime("%Y%m%d").tolist() # 下載大盤資料 df = pd.DataFrame() for month in month_list: url = "https://www.twse.com.tw/indicesReport/MI_5MINS_HIST?response=json&date=" + month res = r.get(url) stock_json = res.json() stock_df = pd.DataFrame.from_dict(stock_json['data']) df = df.append(stock_df, ignore_index = True) # 資料轉型 for col in range(0, 5): for row in range(df.shape[0]): # 把"日期"從字串(string)換成時間(datetime),並將民國年換成西元年 if col == 0: day = df.iloc[row,0].split('/') df.iloc[row, 0] = datetime(int(day[0]) + 1911, int(day[1]), int(day[2])) # 把"開盤價", "最高價", "最低價", "收盤價"帶有逗號的字串(string)換成浮點數(float) elif col != 0: df.iloc[row, col] = float(df.iloc[row,col].replace(',', '')) # 把日期從字串(string)換成時間(datetime),並將民國年換成西元年 df.columns = ['日期', '開盤價', '最高價', '最低價', '收盤價'] return df # In[11]: twse = get_stock_market_price(start_year = 2021, start_month = 9, end_year = 2021, end_month = 10) twse # ## 2.2 下載大盤成交歷史資料 # - 股海小英雄youtube影片 - 大盤成交量:[【Python 爬蟲】台股市場成交資訊免費下載|從成交量判斷大盤進出點](https://youtu.be/JXGl6pfvB-o) # In[12]: #下載大盤成交歷史資料 def get_stock_market_volumn(start_year, start_month, end_year, end_month): start_date = str(date(start_year, start_month, 1)) end_date = str(date(end_year, end_month, 1)) month_list = pd.date_range(start_date, end_date, freq='MS').strftime("%Y%m%d").tolist() # 下載大盤資料 df = pd.DataFrame() for month in month_list: url = "https://www.twse.com.tw/exchangeReport/FMTQIK?response=json&date=" + month res = r.get(url) stock_json = res.json() stock_df = pd.DataFrame.from_dict(stock_json['data']) df = df.append(stock_df, ignore_index = True) # 資料轉型 for col in range(0, 5): for row in range(df.shape[0]): # 把"日期"從字串(string)換成時間(datetime),並將民國年換成西元年 if col == 0: day = df.iloc[row,0].split('/') df.iloc[row, 0] = datetime(int(day[0]) + 1911, int(day[1]), int(day[2])) # 把"成交股數", "成交金額", "成交筆數", "發行量加權股價指數"帶有逗號的字串(string)換成浮點數(float) elif col != 0: df.iloc[row, col] = float(df.iloc[row,col].replace(',', '')) # 把日期從字串(string)換成時間(datetime),並將民國年換成西元年 df.columns = ['日期', '成交股數', '成交金額', '成交筆數', '發行量加權股價指數', '漲跌點數'] return df # In[13]: twse_vol = get_stock_market_volumn(start_year = 2021, start_month = 9, end_year = 2021, end_month = 10) twse_vol # ## 2.3 畫出大盤K線圖與成交金額 # In[14]: # 設定子圖 fig = make_subplots(rows = 2, cols = 1, shared_xaxes = True, vertical_spacing = 0.05, row_width=[0.2, 0.7]) # 畫K線圖 fig.add_trace(go.Candlestick(x = twse['日期'], open = twse['開盤價'], high = twse['最高價'], low = twse['最低價'], close = twse['收盤價'], increasing_line_color = 'red', decreasing_line_color = 'green', name = 'K線圖'), row = 1, col = 1) # 畫成交量長條圖 fig.add_trace(go.Bar(x = twse_vol['日期'], y = twse_vol['成交金額'], showlegend = False, name = '成交金額'), row = 2, col = 1) # 設x軸標題 fig.update_xaxes(rangebreaks = [{ 'pattern': 'day of week', 'bounds': [6, 1]}]) fig.update_xaxes(title_text = "日期", row = 2, col = 1) # 設y軸標題 fig.update_yaxes(title_text = "指數", row = 1, col = 1) # 設圖標及圖長寬 fig.update_layout( title_text = "2021/09 - 2021/10 大盤K線圖", width = 800, height = 400 ) fig.update(layout_xaxis_rangeslider_visible = False) fig.show() # ## 2.4 畫出大盤K線圖與成交金額,標上成交金額的顏色 # In[15]: twse # In[16]: twse['成交金額'] = twse_vol['成交金額'] twse # In[17]: twse["成交金額增減"] = twse['成交金額'].diff() twse # In[18]: twse["成交金額顏色"] = np.where(twse["成交金額增減"] >= 0, 'red', 'green') twse # In[19]: # 第一筆資料沒有成交金額增減,所以當收盤價>=開盤價標示紅色,收盤價<開盤價標示綠色 if twse.iloc[0, 4] - twse.iloc[0, 1] >= 0: twse.iloc[0, 7] = 'red' else: twse.iloc[0, 7] = 'green' # In[20]: twse # In[22]: # 設定子圖 fig = make_subplots(rows = 2, cols = 1, shared_xaxes = True, vertical_spacing = 0.05, row_width=[0.2, 0.7]) # 畫K線圖 fig.add_trace(go.Candlestick(x = twse['日期'], open = twse['開盤價'], high = twse['最高價'], low = twse['最低價'], close = twse['收盤價'], increasing_line_color = 'red', decreasing_line_color = 'green', name = 'K線圖'), row = 1, col = 1) # 畫成交量長條圖 fig.add_trace(go.Bar(x = twse['日期'], y = twse['成交金額'], showlegend = False, marker_color = twse['成交金額顏色'], name = '成交金額'), row = 2, col = 1) # 設x軸標題 fig.update_xaxes(rangebreaks = [{ 'pattern': 'day of week', 'bounds': [6, 1]}]) fig.update_xaxes(title_text = "日期", row = 2, col = 1) # 設y軸標題 fig.update_yaxes(title_text = "指數", row = 1, col = 1) # 設圖標及圖長寬 fig.update_layout( title_text = "2021/09 - 2021/10 大盤K線圖", width = 800, height = 400 ) fig.update(layout_xaxis_rangeslider_visible = False) fig.show()