CCI(Commodity Channel Index)

 

概要
図1 CCIの描画例

1980年にドナルド・M・ランバート氏が開発したオシレータ系テクニカル指標で、商品取引に特化されているため、CCIの名があります。この指標は商品価格の周期的な値動きを見極めるために考案されました。根底には商品には上昇と下落のサイクルがあるという考えがあります。価格の基準値からと基準値の平均から平均偏差を取り、そこからの変動を見て相場の方向性を判断します。図1が表示例となります。CCIはEMAよりトレンド転換のシグナルを早く表示すると言われています。

計算方法(日足の場合)

基準値を最初に計算します。この値はティピカルプライス(TP)です。次にTPのSMAを取りMAを計算します。標準的なnの値は20です。

$$ \rm{} TP = (高値+安値+終値)/3 \\ MA(TPのSMA) = SMA(TP, 20) \\ $$

以上からMAからの平均偏差MD(Mean Deviation)を計算すると、

$$ \rm{} MD = \{(MA-TP_1)+(MA-TP_2)+(MA-TP_3)+…+(MA-TP_{20})\}/20 $$

となります。最後にCCIを計算するためにTPとMAの差をMDで割ります。この時MDには係数0.015倍(慣用的な数字)をかけます。

$$ \rm{} CCI = (TP – MA)/(0.015 \times MD) $$

それでは実際に具体的な値を入れてみましょう。

日数 始値 安値 高値 終値 TP  SMA(TP, 5) MD  CCI  
1日目1000997105710501035
2日目10501040107410701061
3日目10701057107310601063
4日目10601056108210801072
5日目108010781101110010931065
6日目110010951155115011331085
7日目115011121158112011301098
8日目112011131132113011251110
9日目11301094113411001109111826.23-22.37
10日目(最新)11001040111210501064111230.29-106.37

上表のように計算されるので9日目は平常値、10日目は逆張りの機会であると予想できます。

Pythonによる実装

必要なライブラリを読み込みます

!pip install mpl_finance #Collaboratoryに入っていないライブラリを読み込みます
import matplotlib
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
import pandas as pd
import mpl_finance
import sys
import numpy as np
from datetime import datetime
from matplotlib.offsetbox import OffsetImage, AnnotationBbox
import requests
import io

疑似データを読み込みます

#ファイルの読み込み
URL = "https://neulab.co.jp/wp-content/uploads/pseudo_data.csv" #csvファイルのURL

datafile = requests.get(URL)#ファイルの読み込み

#データフレームの作成
df_temp = pd.read_csv(io.BytesIO(datafile.content), header=0, index_col=0, parse_dates=True, encoding="UTF-8")

df = df_temp.loc[:,['Open','High','Low','Close']]
df.head()

CCIを計算します

df['tp'] = df.loc[:,['High', 'Low', 'Close']].mean(axis='columns')
ma_tp = df['tp'].rolling(20).mean()
df['avd_tp'] = (df['tp'] - ma_tp).abs().rolling(20).mean()

df_cci = (df['tp'] - df['tp'].rolling(20).mean())/(0.015 * df['avd_tp'])

matplotを使用した描画例です

canvas_color = '#fffafa'
line_color = '#c8ced1'
font_color = '#171510'
colorup = '#bf0000'
colordown = '#006fbf'

n_data = -100
data = df[n_data:]
ohlc = np.vstack((range(len(data)), data.T)).T

fig, (ax1, ax2) = plt.subplots(2, 1, gridspec_kw={'height_ratios': [10, 6]}, sharex=True, figsize=(12,9))
fig.patch.set_facecolor(canvas_color)
ax1.patch.set_facecolor(canvas_color)
mpl_finance.candlestick_ohlc(ax1, ohlc, width=0.5, alpha=1, colorup=colorup, colordown=colordown)
ax2.patch.set_facecolor(canvas_color)
ax2.plot(range(len(data)), df_cci.values[n_data:], color='red', ls='-', label='CCI(20)')
ax1.grid()
ax2.grid()

#ロゴ読み込み
logoURL = "https://neulab.co.jp/wp-content/uploads/logo.png" #logoファイルのURL
img_c = plt.imread(logoURL)
imagebox = OffsetImage(img_c, zoom=0.020) #画像をimageboxにいれる。
imagebox.image.axes = ax1
im_sabo = AnnotationBbox(imagebox, (0, 9850), xybox=(0, 9950), xycoords="data", boxcoords="data", pad=0.3, frameon=False)

l1,l2 = ax2.get_legend_handles_labels()
ax2.legend(l1,l2, fontsize=14, edgecolor='none', facecolor=canvas_color)

ax1.add_artist(im_sabo)
ax1.set_ylabel("Price of Something", fontsize=22)
ax1.set_ylim(9000., 10000.)
ax1.yaxis.tick_right()
ax1.yaxis.set_label_coords(0, 0.5)
ax1.tick_params(labelsize=24, labelcolor=font_color, color=line_color)

ax1.spines['left'].set_linewidth(0)
ax1.spines['right'].set_linewidth(0)
ax1.spines['top'].set_linewidth(0)
ax1.spines['bottom'].set_linewidth(0)

ax2.yaxis.tick_right()
ax2.set_ylim([-200,200])
ax2.tick_params(labelsize=22, labelcolor=font_color, color=line_color)
#ax2.set_yticks(np.linspace(0,100,6))

ax2.spines['left'].set_color(line_color)
ax2.spines['right'].set_color(line_color)
ax2.spines['top'].set_color(line_color)
ax2.spines['bottom'].set_color(line_color)

xtick0 = 2
plt.xticks(range(xtick0,len(data),12), [x.strftime('%m/%d') for x in df_cci.index][xtick0::12])

plt.subplots_adjust(left=0.05, right=0.89, bottom=0.1, top=0.99)
plt.grid(which='major',color=line_color,linestyle='-')
plt.grid(which='minor',color=line_color,linestyle='-')

ax2.grid(linestyle='--', lw=1)
ax1.set_axisbelow(True)

fig.savefig('CCI.png', facecolor=fig.get_facecolor(), edgecolor='none')

以上のコードをGoogle社の提供しているColaboratory上で公開しており、実際に動作させることができます。

リンク先はこちら

CCIを使った予想

一番簡単な使い方はCCIが-100から100までの間は平常値と考えて、-100と100の範囲を超えたら逆張りで入る方法です。

図2がCCIを使った予想例となります。100や-100を超えたら反転しているのがわかりますが、超えた点で反転しているわけではなく、上下し続けることに注意が必要です。

図2 CCIの予想例
注意点

一口に100を超えたと言っても、CCIはどこで買いが止まるかまでは教えてくれないため、エントリーポイントの見極めが難しい点に注意が必要です。他のテクニカル指標を組み合わせて使用することをお勧めします。


※このHPページで紹介しているテクニカル指標を使った取引ルールや売買シグナルの見方は一般的な考え方に基づくものであり、利益の増加や損失の減少を保証するものではありません。ご自身の判断にてお取引いただきますようお願いいたします。


現在、ニューラボでは人工知能による取引アルゴリズムを開発中です。11月にリリース予定。乞うご期待!
自動取引にご興味を持たれましたら お問い合わせページよりお気軽にお問合せください。