【FX・為替】各国通貨の強弱関係をPythonで可視化してみる

![ダウンロード (3).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/b3e43201-843e-22e0-c60a-acbe83aee261.png)

## 背景

シストレ絶賛勉強中の [@kazama1209](https://qiita.com/kazama1209) です。

以前、自分が裁量トレードを行っていた際、どの通貨ペアで取引するかにおいて「通貨強弱」というものを非常に意識していました。

通貨強弱とは、簡単に言えば「どの通貨が買われていて、どの通貨が売られているのか」という事。

たとえば、「ドル円（USD/JPY）のレートが100円から101円になりました！」という現象が起こった時、その背景では「ドル買い・円売り」が生じています。

効率良く利益を獲得していくためには、強い通貨を買って弱い通貨を売るのが基本です。

もし仮に「強い通貨 × 強い通貨」や「弱い通貨 × 弱い通貨」みたいな通貨ペアを選択してしまうと、強弱関係がハッキリと出ずにレンジ相場で捕まる可能性が高まるでしょう。

手軽に通貨強弱を知れるサイトやインジケーターとしては、

- [Currency Strength Chart](https://currency-strength.com/)
- ku-chart

などが有名ですが、今回は「Currency Strength Chart」を参考に通貨強弱をPythonで可視化してみたいと思います。

## 環境

- Google Colaboratory
    - ブラウザからPythonを記述、実行できるサービス。
- Twelve Data
    - 株、為替、仮想通貨といった金融商品の情報を取得できるサービス。

今回はPythonの実行環境として「[Google Colaboratory](https://research.google.com/colaboratory/)」を使っていきます。

![スクリーンショット 2021-09-19 23.19.07_censored.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/37f3c2d6-468d-016e-fb00-7b26054b8c47.jpeg)

Googleアカウントさえ持っていれば面倒な環境構築の必要も無くそのままPythonを実行していけるので非常に便利です。

また、ヒストリカルデータの取得元としては「[Twelve Data](https://twelvedata.com/)」を採用しました。

![スクリーンショット 2021-09-19 23.20.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/58106eaf-26f8-2b0f-cee9-67d8cdb364db.png)

海外のサービスではありますが、非常に使いやすいAPIを提供してくれている他、取得できる情報も株、為替、仮想通貨と幅広いので何かと便利そうです。

特に為替については国内でデータを取得できるまともなサービスがほとんど存在しないため、有力な選択肢になるのではないでしょうか。（一応、OANDA JAPANなどがAPIを提供しているものの、ある程度の取引量がある人しか利用できなかったりと色々不便だったり...）

![スクリーンショット 2021-09-19 23.17.20_censored.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/ab7d2823-efa4-655c-0a51-1be50eba1686.jpeg)

Twelve DataのAPIキーに関しては、ログイン後のダッシュボードでサクッと発行できるのであらかじめ済ませておいてください。

## コード

それでは、コードを書いていきましょう。

### pip install

```py
pip install twelvedata websocket
```

![スクリーンショット 2021-09-19 23.28.40.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/6aca9217-dce8-5cb0-e834-18b988b0dcac.png)

Google Colaboratory にはすでに一部の基本的なライブラリがあらかじめ標準装備されていたりしますが、上記のライブラリは含まれていないため、「pip install」でインストールしていきます。

### 各種ライブラリの読み込みと設定

```py
import pandas as pd
pd.set_option('display.max_rows', None)
import numpy as np
from twelvedata import TDClient
import time
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
plt.style.use('fivethirtyeight')
plt.rcParams['figure.figsize'] = (20, 10)
```

![スクリーンショット 2021-09-21 5.43.56.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/3e3a339d-850f-373c-56bf-f288b87bb37a.png)


各種ライブラリの読み込みと設定を行います。

### 関数の定義

```py
apikey = 'TWELVE_DATA_API_KEY'
td = TDClient(apikey = apikey)

# ヒストリカルデータを取得
def get_historical_data(symbol):
    interval = '5min' # 時間軸
    outputsize = 2000 # 最大取得件数
    start_date = '2021-09-20 06:00' # 取得開始日（「yyyy-MM-dd」 or 「yyyy-MM-dd hh:mm:ss」）
    end_date = '2021-09-21 05:59' # 取得終了日（「yyyy-MM-dd」 or 「yyyy-MM-dd hh:mm:ss」）
    timezone = 'Asia/Tokyo' # タイムゾーン

    res = td.time_series(symbol = symbol, interval= interval, outputsize = outputsize, start_date = start_date, end_date = end_date, timezone = timezone).as_json()
    
    df = pd.DataFrame(res).iloc[::-1].set_index('datetime').astype(float)
    df = df[df.index >= start_date]
    df.index = pd.to_datetime(df.index)

    return df

# 各通貨の対数変化率を算出
def calc_logarithmic_change_rates(symbols):
    logarithmic_change_rates = []

    for symbol in symbols:
        print(f'Fetching {symbol} ...')
        
        historical_data = get_historical_data(symbol)
        logarithmic_change_rate = np.log(historical_data['close'] / historical_data['close'][0])
        
        logarithmic_change_rates.append(logarithmic_change_rate)

        time.sleep(8) # 無料プランにおけるTwelve DataのAPIコールは1分間に8件までなので間隔を空ける
    
    print('\n Finished !')
    
    return logarithmic_change_rates
```

![スクリーンショット 2021-09-21 6.02.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/0a95c47d-5b70-1371-37e3-454f45424b56.png)


- ヒストリカルデータを取得するための関数
- 各通貨の対数変化率を算出するための関数

をそれぞれ定義していきます。

<font color="Red">※ 対数変化率: ある数値がXからYに変化した際の「log Y/X」（今回は「2021-09-16 06:00」の終値を基準値（X）とし、その後の時刻における終値（Y）がどれだけ変化したかを計算）</font>

### 通貨ペアを指定

```py
# 通貨ペアを指定
symbols = [
    'USD/CAD', 'USD/CHF', 'USD/JPY',
    'EUR/USD', 'EUR/GBP', 'EUR/AUD', 'EUR/NZD', 'EUR/CAD', 'EUR/CHF', 'EUR/JPY',
    'GBP/USD', 'GBP/AUD', 'GBP/NZD', 'GBP/CAD', 'GBP/CHF', 'GBP/JPY',
    'AUD/USD', 'AUD/NZD', 'AUD/CAD', 'AUD/CHF', 'AUD/JPY',
    'NZD/USD', 'NZD/CAD', 'NZD/CHF',  'NZD/JPY',
    'CAD/CHF', 'CAD/JPY',
    'CHF/JPY'
]

usd_cad, usd_chf, usd_jpy, eur_usd, eur_gbp, eur_aud, eur_nzd, eur_cad, eur_chf, eur_jpy, gbp_usd, gbp_aud, gbp_nzd, gbp_cad, gbp_chf, gbp_jpy, aud_usd, aud_nzd, aud_cad, aud_chf, aud_jpy, nzd_usd, nzd_cad, nzd_chf, nzd_jpy, cad_chf, cad_jpy, chf_jpy = calc_logarithmic_change_rates(symbols)
```

![スクリーンショット 2021-09-19 23.53.06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/bf6e7f62-3283-0ca3-074a-3358139614f5.png)


今回は

- USD
- EUR
- JPY
- GBP
- AUD
- CHF
- CAD
- NZD

の強弱を求めたいので、上記の通貨ペアを指定しつつ対数変化率を算出してきます。

### 通貨単体の強さを算出

```py
# 通貨単体の強さを算出
usd = ((eur_usd * (-1)) + (aud_usd * (-1)) + (gbp_usd * (-1)) + (nzd_usd * (-1)) + usd_cad + usd_chf + usd_jpy).fillna(method = "ffill")
eur = (eur_usd + eur_gbp + eur_aud + eur_nzd + eur_cad + eur_chf + eur_jpy).fillna(method = "ffill")
jpy = ((usd_jpy * (-1)) + (eur_jpy * (-1)) + (gbp_jpy * (-1)) + (aud_jpy * (-1)) + (nzd_jpy * (-1)) + (cad_jpy * (-1)) + (chf_jpy * (-1))).fillna(method = "ffill")
gbp = ((eur_gbp * (-1)) + gbp_usd + gbp_aud + gbp_nzd + gbp_cad + gbp_chf + gbp_jpy).fillna(method = "ffill")
aud = ((eur_aud * (-1)) + (gbp_aud * (-1)) + aud_usd + aud_nzd + aud_cad + aud_chf + aud_jpy).fillna(method = "ffill")
chf = ((usd_chf * (-1)) + (eur_chf * (-1)) + (gbp_chf * (-1)) + (aud_chf * (-1)) + (nzd_chf * (-1)) + (cad_chf * (-1)) + chf_jpy).fillna(method = "ffill")
cad = ((usd_cad * (-1)) + (eur_cad * (-1)) + (gbp_cad * (-1)) + (aud_cad * (-1)) + (nzd_cad * (-1)) + cad_chf + cad_jpy).fillna(method = "ffill")
nzd = ((eur_nzd * (-1)) + (gbp_nzd * (-1)) + (aud_nzd * (-1)) + nzd_usd + nzd_cad + nzd_chf + nzd_jpy).fillna(method = "ffill")
```

![スクリーンショット 2021-09-19 23.54.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/5f5f238a-595e-9aef-480b-451e3452eb73.png)

通貨単体の強さについては、先ほど算出した対数変化率の和で求める事ができます。
主軸通貨でない場合は「-1」を掛ける事で数値を反転させてください。

<font color="Red">※ 主軸通貨: 通貨ペアの前部分。たとえば、USD/JPYであれば「USD」が主軸通貨となる。一方で「JPY」は決済通貨と呼ばれる。</font>

### 通貨の強弱関係を描画

```py
# 通貨の強弱関係を描画
fig, ax = plt.subplots()

ax.plot(usd.index, usd, label = 'USD', color = 'orange', linewidth = 1)
ax.plot(eur.index, eur, label = 'EUR', color = 'red', linewidth = 1)
ax.plot(jpy.index, jpy, label = 'JPY', color = 'aqua', linewidth = 1)
ax.plot(gbp.index, gbp, label = 'GBP', color = 'limegreen', linewidth = 1)
ax.plot(aud.index, aud, label = 'AUD', color = 'blue', linewidth = 1)
ax.plot(chf.index, chf, label = 'CHF', color = 'brown', linewidth = 1)
ax.plot(cad.index, cad, label = 'CAD', color = 'blueviolet', linewidth = 1)
ax.plot(nzd.index, nzd, label = 'NZD', color = 'deeppink', linewidth = 1)
ax.xaxis.set_major_formatter(mdates.DateFormatter('%H:%M'))

ax.legend()
plt.show()
```

![スクリーンショット 2021-09-20 0.13.55.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/3210c8ea-902a-215a-1c8d-fde319987d30.png)

最後に各通貨の強さを描画して完成です。

**今回作成したチャート**

![ダウンロード (3).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/885381d2-4923-8c33-dd7c-b66817031877.png)

**Currency Strength Chart**

![スクリーンショット 2021-09-21 5.45.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/edf84ec2-7684-b82a-40e1-3df78a2cb098.png)


2つを比較してもおおむね合っていそうですね。微妙に異なっている部分もありますが、データ取得元の取引所などによってレートの表示が違ったりするので多少は目を瞑りたいところです。

十分に実用範囲なので今回は良しとしましょうか。

この日のチャートを見てみると、日本円（JPY）とスイスフラン（CHF）の強さが目立ちます。一体何があったのかというと、どうやら中国の不動産大手「恒大集団」が経営破綻の危機に陥ってるらしく、それを受けて世界的な株安となったようですね。

https://www.nikkei.com/article/DGXZQOGM201CE0Q1A920C2000000/

いわゆるリスクオフ相場というヤツです。こういった曲面では円やスイスフランといった安全資産が買われ、リスク資産の資源国通貨（豪ドルやカナダドルなど）が売られる傾向となるので、非常に典型的な相場だった事がわかります。

特にオーストラリアは貿易における中国との結びつきが非常に強いため、この日は全体で見ても弱めの通貨となったわけですね。

![IMG_2455.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/688854/6864763b-b854-4bcb-8fe6-e647706e1c3b.png)


強い通貨を買って、弱い通貨を売るという戦略に従うと、豪ドル円（AUD/JPY）などのショート（売り）を仕掛ければ勝率は比較的高かったと考えられるでしょう。

## あとがき

以上、各通貨の強弱関係をPythonで可視化してみました。

あくまでトレンドを掴むための指標であり、具体的なエントリータイミングを推し量れるものではありませんが、どの通貨ペアで取引すべきなのかといった方向性が見えるだけでも有効活用はできそうです。

通貨の強さがデータとして扱えれば、今後シストレに組み込んでいく事も可能なはずなので色々模索したいところ...。