본문 바로가기

데이터분석 with 파이썬/데이터분석실습

과거 주식 패턴을 이용한 돌팔이 수익률 예측 모델

stockpredict_0501
In [2]:
import pandas as pd
import numpy as np
from pandas import DataFrame 
from pandas import Series
from datetime import datetime
import matplotlib.pyplot as plt
%matplotlib inline
In [3]:
def f(x): 
        return datetime.strptime(x,'%Y%m%d')
In [4]:
path = "{0}-m-00001".format("130960")
print(path)
try:
    df = pd.read_table(path,header=None)
except Exception : 
    print('no FIle')
    
df = df.dropna()    
df2 = df[0].astype('U') #타임스태프를 위해 문자열 변환
timeindex = df2.apply(f) #타임스태프 변환
df3=df.rename(timeindex) #인덱스를 타임스태프로 
data = df3.drop(0,axis=1) #기본 시간은 제거
data = DataFrame(data)
data = data.sort_index(ascending=True)
130960-m-00001
In [5]:
traindata = data.ix[:int(len(data)*(4/5)),1]  # train data 
testdata = data.ix[int(len(data)*(4/5)):,1]   # test data 나누기
In [6]:
interval = 4  #분석할 일자 간격 4일 단위
In [7]:
def percentChange(startPoint,currentPoint):
    try:
        x = ((float(currentPoint)-startPoint)/abs(startPoint))*100.00
        if x == 0.0:
            return 0.000000001 #극단치 제거
        else:
            return x
    except:
        return 0.0001
In [8]:
x=int(len(traindata))-interval
y=interval
realprice_trainset=[]  #실제 가격 set
ratepattern_trainset =[] # 현시점에서 각 수익률 set
outpattern_trainset=[]  # 현시점 다음 값에서 평균을 낸 미래 수익률 
out_avg_trainset=[]     # 그 수익률의 평균
while(y<x):
    pattern=[]
    outpattern=[]
    realprice=[]
    our_avg_set=[]
    for i in range(interval):
        realprice.append(traindata.ix[y-interval+i,1])
        pattern.append(percentChange(traindata.ix[y-interval,1],traindata.ix[y-interval+1+i,1]))
        outpattern.append(percentChange(traindata.ix[y,1],traindata.ix[y+i+1,1]))
    realprice_trainset.append(realprice)
    ratepattern_trainset.append(pattern)
    outpattern_trainset.append(outpattern)
    out_avg_trainset.append(np.average(outpattern[:2]))
    y=y+1
In [9]:
x=int(len(testdata))-interval
y=interval
realprice_testset=[]
ratepattern_testset =[]
outpattern_testset=[]
out_avg_testset=[]
while(y<x):
    pattern=[]
    outpattern=[]
    realprice=[]
    our_avg_set=[]
    for i in range(interval):
        realprice.append(testdata.ix[y-interval+i,1])
        pattern.append(percentChange(testdata.ix[y-interval,1],testdata.ix[y-interval+i,1]))
        outpattern.append(percentChange(testdata.ix[y,1],testdata.ix[y+i+1,1]))
    realprice_testset.append(realprice)
    ratepattern_testset.append(pattern)
    outpattern_testset.append(outpattern)
    out_avg_testset.append(np.average(outpattern[:2]))
    y=y+1
In [10]:
def uclid (each,test) : # 각 패턴의 유사도에 유클리드(거리)의 개념 추가
    conflict=0
    if abs(each-test).max()>1.5 : #remove extream rate
        return 100
    for i in range(len(each)):
        if each[i]*test[i]<0:
            conflict+=1
    if conflict>int(interval/8): #t상관계수만으로는 모양만 같고 수익률의 부호가 다를 수 있으므로 곱의 - 가 되는 모순점 계측
        return 100
    if((each[len(each)-1]-each[len(each)-2])*(test[len(test)-1]-test[len(test)-2])<0):  #마지막 모멘텀이 비슷해야하는 조건 추가
        return 100
    return abs(each-test).mean()
    
In [20]:
def simpattern (train_set=[],test=[]):  #유사도 찾는 함수
    test = Series(test)
    simPattern_set =[]
    simPattern_index=[]
    
    for i,eachpattern in enumerate(train_set):
        each = Series(eachpattern)
        if((np.corrcoef(each,test)[0,1]>.8) and uclid(each,test)<2.5):  #상관계수와 유클리드 유사도를 이용한 유사패턴 탐색
            simPattern_set.append(each)
            simPattern_index.append(i)
    return simPattern_set,simPattern_index
    
    
In [21]:
## 유사패턴 찾는 예시   test 패턴의 7번째에 대해 유사한 그래프를 train data에서 추출 
simPattern_set,simPattern_index=simpattern(ratepattern_trainset,ratepattern_testset[7])
for i in range(len(simPattern_index)-10):
    plt.figure(i)
    plt.plot(ratepattern_testset[7],color='red') #빨간색이 현재 패턴 
    plt.plot(simPattern_set[i]) #과거에 데이터에서 찾아진 유사패턴
16
In [11]:
# for i in range(len(simPattern_set)):
#     plt.figure(i)
#     plt.plot(ratepattern_testset[17],color='red')
#     plt.plot(simPattern_set[i])
In [22]:
def mean_out_avg (simPattern_index=[]):
    if len(simPattern_index)==0 : return 0 #if there is no pattern
    
    total=0
    for i in simPattern_index:
        total =total+out_avg_trainset[i]
    return total/len(simPattern_index)
    
In [23]:
heatarr= np.array([[0,0],[0,0]])
for i in range(len(ratepattern_testset)):
    simPattern_set, simPattern_index = simpattern(ratepattern_trainset,ratepattern_testset[i])
    predict = mean_out_avg(simPattern_index)
    
    if (predict==0) : continue
    real = out_avg_testset[i]
    if (predict>0 and real>0):
        heatarr[0,1]+=1
    elif (predict<0 and real<0):
        heatarr[1,0]+=1
    elif (predict>0 and real<0):
        heatarr[0,0]+=1
    elif (predict<0 and real>0):
        heatarr[1,1]+=1
    
In [24]:
heatarr  ## (0,0) 음수를 양수로 판단 (0,1) 양수를 양수로 판단 (1,0) 음수를 음수로 판단 (1,1) 양수를 음수로 판단
Out[24]:
array([[66, 57],
       [43, 44]])
In [ ]:
# 딱 반반으로 이 모델은 망했다는 것을 알 수 있다. 그러나 유사패턴을 찾는 모듈은 어느정도 성공~!
In [ ]:
 
In [ ]:
 
In [ ]:
 
In [ ]: