Google colaboratory上でpandas-datareaderを用いて東証上場銘柄の株価を取得する

## 1.Google colaboratoryについて
・Googleが提供するSaas型Python実行環境サービス。
・Googleアカウント（Google Drive）があれば利用可能。
・Google colaboratoryの利用は、原則**無料**（←<font color=red>ココ重要</font>）
・Google colaboratoryは、機械学習を試したい場合に必要なライブラリが標準で既に入っている。機械学習の初学者は言うまでもなく、Python初学者にとっても、Python環境のセットアップを省略して即Python実行環境でお試し実行が可能。
・機械学習や深層学習をおこなう際の演算処理にGPUが利用可能。つまりGoogleの巨大なリソースが無料で利用可能（≒ ~~Google神の下僕or小作人になってGoogle大地主様の広大なプランテーションが利用可能。ビバ！「**クラウドの衝撃**」！~~）

・自分のGoogleアカウントのGoogle Drive上にあるJupyter notebookのファイル(.ipynb)を実行することで、裏側で稼働するGoogle様のリソースを利用してPythonプログラムを実行する的なイメージ。
・インスタンスはCPUで1個、GPUで1個、合計2個のインスタンスが起動できる。
・インスタンスの連続処理は12時間でいったんリセット再起動される。またブラウザのセッションは90分で切れる。
・Google colaboratoryはSaas型クラウドサービスなので、例えばローカルPCのRDBを利用するといった用途には向いていない。上述のインスタンスは最長12時間後にリセットされデータ等がきれいさっぱり消えてしまうので、データの永続化をおこないたい場合は、Google Driveにファイルを退避しておくか、あるいはGoogleのBigQueryなどクラウド上のDBサービスを利用するなどしておくのがよろしい。
## 2.日本取引所グループのHPにある東証上場銘柄一覧(月次)のExcelファイルから対象銘柄を用意する
　日本取引所グループ（というか東京証券取引所）は、月に１回の頻度で東証に上場している銘柄一覧（ETF/ETN/J-REITなど含む）をExcelファイルで公開している。
![test20180710.png](https://qiita-image-store.s3.amazonaws.com/0/91974/47cd02ad-50a9-b008-8522-b00427ae3601.png)

※日本取引所グループHP
[統計情報（株式関連）]-[統計資料]-[東証上場銘柄一覧]
https://www.jpx.co.jp/markets/statistics-equities/misc/01.html

このExcelファイルをpandasのread_excel()を使ってGoogle colaboratory上で読み込んで、東証に上場している銘柄一覧のdataframeオブジェクトを生成するといった処理を記述したのが、以下のコード↓

```python:test.py
#事前処理
#!pip list
!pip install -q xlrd
!pip install pandas_datareader

###############################################
# Jupyter_notebook's Shortcut
# Ctrl + \ :すべてのランタイムをリセット[←ショートカットを任意に割り振り]
# Ctrl + Enter :セルを実行
###############################################

from google.colab import files

import google.colab
import googleapiclient.discovery
import googleapiclient.http

import datetime

import pandas as pd
import pandas_datareader.data as web

#JPXの東証上場一覧のページへのアクセス
!wget 'https://www.jpx.co.jp/markets/statistics-equities/misc/tvdivq0000001vg2-att/data_j.xls' -O data_j.xls -a wget-log

## pandasでexcelファイルの読み込みとdf整形など
df = pd.read_excel( "data_j.xls" ) 
df.columns = ['date','code','name','lst','sectorCode','sectorName', 'flr1', 'flr2', 'flr3', 'flr4']
drop_col = ['flr1', 'flr2', 'flr3', 'flr4'] 
df = df.drop(drop_col , axis=1) #不要な列の削除

## dfのグルーピングとグループ指定(1グループ240銘柄に限定する)
j = 1 #17
df['id'] = (df.index/240)+1  # グルーピング
x = df[df['id'] == j]
print( x.iloc[:,1] )
```
・Google colaboratoryでLinuxコマンドを実行する場合、コマンドの先頭に「**！**」を付ける （<font color=red>!pip</font>や<font color=red>!wget</font>など）
・Google colaboratoryで、カレントディレクトリは変更できなさそう。
・Google colaboratoryにすでに入っているライブラリはpip installは不要。Google colaboratoryに入っていないライブラリは処理の先頭でpip installをしておく。Google colaboratoryはインスタンスが12時間でリセットされるので、都度pip installをするイメージ。（すでに入っているライブラリはpip installをしてもそこでエラーにはならない的な...）
・上記のコードでpipコマンドでインストールするのは、excelファイルを扱うためのライブラリ「xlrd」と、株価を取得するためのライブラリ「pandas-datareader」の２つ。
・日本取引所のホームページで公開されている東証上場一覧のExcelファイルをwgetでダウンロードする。
・pandasはGoogle colaboratoryに既に入っているのでpip install不要。
・pandasのread_excel()を使ってwgetで取得したExcelファイルを読み込み
・使う列に名前付与。ファイル生成日と証券コード、銘柄名、業種と業種コードをとりあえず利用して、他の列は不要なのでflr1〜flr4と命名した上でdfから列削除。
・あと後続の処理のために、df、つまり銘柄一覧を240個ずつにグルーピングして任意のグループに限定、dfの行を240行に絞り込み。
## 3.pandas-datareader(stooq)を使って株価を取得する
　pandas-datareaderというライブラリで株価や日経平均株価、為替や金利などが取得可能。以下にトヨタ自動車(証券コード：7203)の株価をstooqという東欧の企業が公開しているデータセットを利用して取得するコードを記す。

```python:example_stooq.py
!pip install pandas_datareader
import pandas_datareader.data as web
df = web.DataReader('7203.JP' , "stooq" )
print(df.head(20))

```
 pandas-datareaderでstooqの株価を取得するには、上記のように引数にティッカーシンボル（日本の銘柄の場合は証券コードに「.JP」を付与したもの）を1銘柄指定する方法の他に、ティッカーシンボルの文字列のリストを引数に指定することも可能。それを踏まえて、上記の東証上場銘柄一覧を取得したdataframe(df)をリスト化してpandas-datareaderで複数銘柄のstooq株価を取得したのが、下記のコード。

```python:test2.py
### dfをリスト化 / 中身を文字型に変換して'.JP'を付与
li = x.iloc[:,1].values.tolist()
lst =  [str(i)+'.JP' for i in li]
# print( lst )
# ex) lst = ['1301.JP','7203.JP','6758.JP','7974.JP']

df= web.DataReader(lst , "stooq" )
print(len(df.index))
tgt = df["Close"]
#print(tgt)

# csv保存：listed_yyyymmdd_j.csv
now = datetime.datetime.now()
yyyymmdd = now.strftime("%Y%m%d")
filename = "listed_" + str(yyyymmdd) + "_" + str(j) + ".csv"
tgt.to_csv(filename , encoding="utf-8")
print('saved_csv finish!')
```
・dfからstooqの引数に必要な列は証券コードなので、iloc()で２列目をリスト化して中身を文字型に変換して「.JP」の文字列を追加付与。lstは`['1301.JP','7203.JP','6758.JP','7974.JP']`みたいなイメージの文字列のリスト（銘柄数は上記の処理で240個に限定）。
・DataReaderに上記lstを引数に指定してstooqの株価を取得すると、xyzと３次元のdataframeオブジェクトが返ってくる。上記では終値に限定して２次元(date × code)のdfにしている。

・stooqの株価は、取得銘柄数に上限がある模様。一定数を超えて株価を取得しようとすると、空のdataframeオブジェクトが返ってくるようになる（ので240個の銘柄に限定）
・stooqの株価は、株式分割や株式併合の調整を実施した値の模様。あと前営業日の株価が取得可能。
・pandasのto_csv()を使ってdfの結果をcsvファイルとして生成。


## 4.csvファイルをGoogle Driveに格納する

```python:test3.py
#ファイルアップロード ※for adc.json
f=files.upload()
  
/# Google Drive認証
google.colab.auth.authenticate_user()
drive_service = googleapiclient.discovery.build('drive', 'v3')

/# Google Driveにファイルコピー
file_metadata = {
  'name': filename,
  'mimeType': 'application/octet-stream'
}
media=googleapiclient.http.MediaFileUpload(filename, 
                        mimetype='application/octet-stream',
                        resumable=True)
created = drive_service.files().create(body=file_metadata,
                        media_body=media,    
                        fields='id').execute()
print('All_finish!')

```
・Google colaboratoryは12時間後に、インスタンス再起動してファイル等がきれいになくなってしまうので、自分のGoogleアカウントで認証してGoogleドライブに接続して、上記で生成したcsvファイルをコピー
・毎回Googleの認証をwebブラウザで通すのが超煩雑なので、認証時にtokenファイル(adc.json)が生成されるので、そのtokenファイル、adc.jsonを退避させておいて初回にGoogle colaboratoryの環境にファイルアップロードしている。（２回目以降はGoogleのwebでの認証はショートカットされる）
・あるいはcsvファイルを生成してgoogle Driveにファイルコピーするのがまどろっこしい場合は、pandasのto_gbq()を用いてdfデータをGoogle Bigqueryに格納するのも一案かもしれない(注：Google BigQueryは有償です)

## 5.補足
・なぜGoogle colaboratoryを利用するのかというと、pandas-datareaderというかstooqの株価取得には利用制限があるようなので、Google colaboratoryのインスタンスを再起動することによって、世界のどこかで実際に処理が走るであろうGoogleのサーバー（のIPアドレス？）を都度変更して、stooqの株価取得の利用制限をクリアするため...以下自重、推して量るべし。
・日本取引所が公開している東証上場銘柄は、ETF/ETN/J-REITを含めて大体約4000銘柄あるので、stooqの株価取得上限がおよそ240とすると、上記で分けたグループ数は17(＝16.6)なので、17回ほどpandas-datareaderのstooq株価取得とGoogle colaboratoryのインスタンスの再起動を繰り返せば全銘柄の株価が取得可能かと思わr...以下自重、推して量るべし。
・あとライザップ(証券コード：2928)は、札幌証券取引所上場銘柄なので、上記のExcelファイルには載ってないです。

※参考：stooq↓
https://stooq.pl