바이낸스 선물 다화폐 헤지 전략의 최근 검토와 분자 수준의 K 라인 백테스트 결과
바이낸스의 멀티 화폐 헤지 전략에 대한 세 가지 연구 보고서는 출판되었으며, 다음은 네 번째입니다. 첫 번째 세 개의 기사의 연결, 당신이 그것을 읽지 않은 경우 다시 읽어야합니다, 당신은 전략의 형성 아이디어를 이해할 수 있습니다. 특정 매개 변수 설정 및 전략 논리.
바이낸스 선물 다화폐 헤지 전략 연구 1부:https://www.fmz.com/digest-topic/5584
바이낸스 선물 다화폐 헤지 전략 연구 2부:https://www.fmz.com/digest-topic/5588
바이낸스 선물 다화폐 헤지 전략 연구 3부:https://www.fmz.com/digest-topic/5605
이 기사는 최근 주의 실제 시장 상황을 검토하고 이익과 손실을 요약합니다. 지난 두 달 동안 바이낸스 선물 분 K 라인 데이터를 탐색한 후, 일부 매개 변수 설정의 의미를 더 잘 설명 할 수있는 원래 1h K 라인 백테스트 결과를 업데이트 할 수 있습니다.
# Libraries to import
import pandas as pd
import requests
import matplotlib.pyplot as plt
import seaborn as sns
import numpy as np
%matplotlib inline
symbols = ['BTC','ETH', 'BCH', 'XRP', 'EOS', 'LTC', 'TRX', 'ETC', 'LINK', 'XLM', 'ADA', 'XMR', 'DASH', 'ZEC', 'XTZ', 'BNB', 'ATOM', 'ONT', 'IOTA', 'BAT', 'VET', 'NEO', 'QTUM', 'IOST']
2월 21일부터 4월 15일 오후 2시까지의 데이터, 총 77160 * 24, 우리의 백테스트 속도를 크게 줄인, 백테스트 엔진은 충분히 효율적이지 않습니다, 당신은 그것을 스스로 최적화 할 수 있습니다.
price_usdt = pd.read_csv('https://www.fmz.com/upload/asset/2b1fa7ab641385067ad.csv',index_col = 0)
price_usdt.shape
(77160, 24)
price_usdt.index = pd.to_datetime(price_usdt.index,unit='ms')
price_usdt_norm = price_usdt/price_usdt.fillna(method='bfill').iloc[0,]
price_usdt_btc = price_usdt.divide(price_usdt['BTC'],axis=0)
price_usdt_btc_norm = price_usdt_btc/price_usdt_btc.fillna(method='bfill').iloc[0,]
class Exchange:
def __init__(self, trade_symbols, leverage=20, commission=0.00005, initial_balance=10000, log=False):
self.initial_balance = initial_balance # Initial asset
self.commission = commission
self.leverage = leverage
self.trade_symbols = trade_symbols
self.date = ''
self.log = log
self.df = pd.DataFrame(columns=['margin','total','leverage','realised_profit','unrealised_profit'])
self.account = {'USDT':{'realised_profit':0, 'margin':0, 'unrealised_profit':0, 'total':initial_balance, 'leverage':0, 'fee':0}}
for symbol in trade_symbols:
self.account[symbol] = {'amount':0, 'hold_price':0, 'value':0, 'price':0, 'realised_profit':0, 'margin':0, 'unrealised_profit':0,'fee':0}
def Trade(self, symbol, direction, price, amount, msg=''):
if self.date and self.log:
print('%-20s%-5s%-5s%-10.8s%-8.6s %s'%(str(self.date), symbol, 'buy' if direction == 1 else 'sell', price, amount, msg))
cover_amount = 0 if direction*self.account[symbol]['amount'] >=0 else min(abs(self.account[symbol]['amount']), amount)
open_amount = amount - cover_amount
self.account['USDT']['realised_profit'] -= price*amount*self.commission # Minus handling fee
self.account['USDT']['fee'] += price*amount*self.commission
self.account[symbol]['fee'] += price*amount*self.commission
if cover_amount > 0: # close position first
self.account['USDT']['realised_profit'] += -direction*(price - self.account[symbol]['hold_price'])*cover_amount # profit
self.account['USDT']['margin'] -= cover_amount*self.account[symbol]['hold_price']/self.leverage # Free margin
self.account[symbol]['realised_profit'] += -direction*(price - self.account[symbol]['hold_price'])*cover_amount
self.account[symbol]['amount'] -= -direction*cover_amount
self.account[symbol]['margin'] -= cover_amount*self.account[symbol]['hold_price']/self.leverage
self.account[symbol]['hold_price'] = 0 if self.account[symbol]['amount'] == 0 else self.account[symbol]['hold_price']
if open_amount > 0:
total_cost = self.account[symbol]['hold_price']*direction*self.account[symbol]['amount'] + price*open_amount
total_amount = direction*self.account[symbol]['amount']+open_amount
self.account['USDT']['margin'] += open_amount*price/self.leverage
self.account[symbol]['hold_price'] = total_cost/total_amount
self.account[symbol]['amount'] += direction*open_amount
self.account[symbol]['margin'] += open_amount*price/self.leverage
self.account[symbol]['unrealised_profit'] = (price - self.account[symbol]['hold_price'])*self.account[symbol]['amount']
self.account[symbol]['price'] = price
self.account[symbol]['value'] = abs(self.account[symbol]['amount'])*price
return True
def Buy(self, symbol, price, amount, msg=''):
self.Trade(symbol, 1, price, amount, msg)
def Sell(self, symbol, price, amount, msg=''):
self.Trade(symbol, -1, price, amount, msg)
def Update(self, date, close_price): # Update assets
self.date = date
self.close = close_price
self.account['USDT']['unrealised_profit'] = 0
for symbol in self.trade_symbols:
if np.isnan(close_price[symbol]):
continue
self.account[symbol]['unrealised_profit'] = (close_price[symbol] - self.account[symbol]['hold_price'])*self.account[symbol]['amount']
self.account[symbol]['price'] = close_price[symbol]
self.account[symbol]['value'] = abs(self.account[symbol]['amount'])*close_price[symbol]
self.account['USDT']['unrealised_profit'] += self.account[symbol]['unrealised_profit']
self.account['USDT']['total'] = round(self.account['USDT']['realised_profit'] + self.initial_balance + self.account['USDT']['unrealised_profit'],6)
self.account['USDT']['leverage'] = round(self.account['USDT']['margin']/self.account['USDT']['total'],4)*self.leverage
self.df.loc[self.date] = [self.account['USDT']['margin'],self.account['USDT']['total'],self.account['USDT']['leverage'],self.account['USDT']['realised_profit'],self.account['USDT']['unrealised_profit']]
전략 코드는 4월 10일에 위ቻ 그룹에서 공개되었다. 초기에는 한 그룹이 전략 2 (short over-rise and long over-fall) 을 실행했다. 첫 3일 동안 수익률은 매우 좋았고, 회수율은 매우 낮았다. 다음 날에는 일부 거래자가 레버리지를 확대했고, 일부는 자금의 전체 금액을 사용하기도 했으며, 수익률은 하루 만에 10%에 달했다. 전략 스퀘어는 또한 많은 실제 시장 전략을 발표했으며, 많은 사람들이 보수적인 권장 매개 변수에 불만을 느끼기 시작했고 거래량을 증폭시켰다. 4월 13일 이후, BNB
전략 2의 전체 통화 백테스트를 살펴 보겠습니다. 여기서, 그것은 분자 수준의 업데이트이기 때문에 알파 매개 변수를 조정해야합니다. 실제 시장 관점에서, 곡선 추세는 일관적입니다. 우리의 백테스트가 강력한 기준으로 사용될 수 있음을 나타냅니다. 순액은 4.13 이후 순액의 최고점에 도달했으며 후퇴 및 측면 단계에있었습니다.
Alpha = 0.001
#price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.rolling(20).mean() # Ordinary moving average
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 300
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 0.5*trade_value:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < -0.5*trade_value:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2a = e
(stragey_2a.df['total']/stragey_2d.initial_balance).plot(figsize=(17,6),grid = True);
전략 1, 코트 Altcoin 전략은 긍정적 인 수익을 달성
trade_symbols = list(set(symbols)-set(['LINK','BTC','XTZ','BCH', 'ETH'])) # Selling short currencies
e = Exchange(trade_symbols+['BTC'],initial_balance=10000,commission=0.00075,log=False)
trade_value = 2000
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
empty_value = 0
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
if e.account[symbol]['value'] - trade_value < -120 :
e.Sell(symbol, price, round((trade_value-e.account[symbol]['value'])/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if e.account[symbol]['value'] - trade_value > 120 :
e.Buy(symbol, price, round((e.account[symbol]['value']-trade_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
empty_value += e.account[symbol]['value']
price = row[1]['BTC']
if e.account['BTC']['value'] - empty_value < -120:
e.Buy('BTC', price, round((empty_value-e.account['BTC']['value'])/price,6),round(e.account['BTC']['realised_profit']+e.account['BTC']['unrealised_profit'],2))
if e.account['BTC']['value'] - empty_value > 120:
e.Sell('BTC', price, round((e.account['BTC']['value']-empty_value)/price,6),round(e.account['BTC']['realised_profit']+e.account['BTC']['unrealised_profit'],2))
stragey_1 = e
(stragey_1.df['total']/stragey_1.initial_balance).plot(figsize=(17,6),grid = True);
전략 2 장기적 부진을 구매하고 단기적 부진을 판매
최종 계좌 정보를 인쇄하면 대부분의 통화가 이익을 가져왔고 BNB는 가장 많은 손실을 입었습니다. 이것은 또한 BNB가 독립적인 경향의 물결에서 벗어나서 많이 상승하고 가장 큰 편차가 0.06이기 때문입니다.
pd.DataFrame(stragey_2a.account).T.apply(lambda x:round(x,3)).sort_values(by='realised_profit')
# BNB deviation
(price_usdt_btc_norm2.iloc[-7500:].BNB-price_usdt_btc_norm_mean[-7500:]).plot(figsize=(17,6),grid = True);
#price_usdt_btc_norm_mean[-7500:].plot(figsize=(17,6),grid = True);
BNB와 ATOM을 제거하면 더 좋은 결과가 나오지만, 전략은 아직 최근에는 리트레이싱 단계에 있을 것입니다.
Alpha = 0.001
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols)-set(['BNB','ATOM']))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 300
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 0.5*trade_value:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < -0.5*trade_value:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2b = e
(stragey_2b.df['total']/stragey_2b.initial_balance).plot(figsize=(17,6),grid = True);
지난 2 일 동안 주류 통화 전략을 실행하는 것이 인기가되었습니다. 이 전략을 백테스트 해 봅시다. 통화 다양성의 감소로 인해 거래 가치는 비교를 위해 적절히 4 배 증가했으며 최근 리트레이션이 작았기 때문에 결과가 잘되었습니다.
참고로 주류 통화만이 더 긴 시간 백테스트에서 전체 통화만큼 좋지 않으며 더 많은 리트레이션이 있음을 유의해야합니다. 주류 화폐가 덜 분산되어 변동성이 증가하기 때문에 아래 시간 라인에 자신의 백테스트를 수행 할 수 있습니다.
Alpha = 0.001
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = ['ETH','LTC','EOS','XRP','BCH']
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 1200
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 0.5*trade_value:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < -0.5*trade_value:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2c = e
(stragey_2c.df['total']/e.initial_balance).plot(figsize=(17,6),grid = True);
처음 몇 보고서는 시간 수준 k 라인을 사용 하 고 실제 매개 변수는 실제 시장 상황과 매우 다르기 때문에, 이제 분 수준 k 라인을 통해, 당신은 몇 가지 매개 변수를 설정하는 방법을 볼 수 있습니다. 먼저 기본 매개 변수 설정을 살펴:
알파 = 0.03 지수 이동 평균의 알파 매개 변수. 설정이 커질수록 벤치마크 가격 추적이 더 민감하고 거래가 적습니다. 최종 보유 지위는 또한 낮아지므로 레버리지가 감소하지만 수익률과 최대 리트레이싱도 감소합니다.
Update_base_price_time_interval = 30 * 60 알파 매개 변수와 관련하여 초로 기본 가격을 얼마나 자주 업데이트합니까? 알파 설정이 작을수록 간격이 작을 수 있습니다.
트레이드_밸류: 알트코인 가격의 (BTC로 표기된) 1%마다 투입된 총 자금과 위험 선호도에 따라 결정되어야하는 지수 보유 가치에서 벗어나게 됩니다. 총 자금의 3-10%를 설정하는 것이 좋습니다. 연구 환경의 백테스트를 통해 레버의 크기를 살펴볼 수 있습니다. 트레이드_밸류는 Adjust_value의 절반과 같은 Adjust_value의 절반보다 작을 수 있습니다. 이는 지수에서 2%의 보유 가치와 동등합니다.
조정_값: 계약 가치 (USDT 평가) 는 오차 값을 조정합니다. 지수가 * 트레이드_값-현재 위치> 조정_값에서 오차 할 때, 즉 목표 위치와 현재 위치 사이의 차이는이 값을 초과하면 거래가 시작됩니다. 너무 큰 조정이 느리고 너무 작은 거래가 빈번하며 10보다 작을 수 없습니다. 그렇지 않으면 최소한의 거래가 달성되지 않으면 트레이드_값의 40% 이상으로 설정하는 것이 좋습니다.
Trade_value는 우리의 수익과 위험과 직접적으로 관련이 있습니다. Trade_value가 변경되지 않은 경우, 지금까지 수익성이 있어야 합니다.
알파는 이번엔 더 높은 주파수 데이터를 가지고 있기 때문에 1분마다 업데이트하는 것이 더 합리적입니다. 물론 원래보다 작습니다. 구체적인 숫자는 백테스트로 결정할 수 있습니다.
Adjust_value는 항상 Trade_value의 40% 이상을 권장했습니다. 원래 1h K 라인 설정은 거의 효과가 없습니다. 일부 사람들은 목표 위치에 더 가까이있을 수 있도록 매우 낮게 조정하기를 원합니다. 여기서는 왜 그렇게해서는 안되는지 분석 할 것입니다.
먼저 수수료 처리 문제를 분석
0.00075의 기본 비율 아래에서 처리 수수료는 293이고 이윤은 270이므로 매우 높은 비율입니다. 우리는 처리 수수료를 0으로 설정하고 10을 조정합니다.
stragey_2a.account['USDT']
{'fee': 293.85972778530453,
'leverage': 0.45999999999999996,
'margin': 236.23559736312995,
'realised_profit': 281.77464608744435,
'total': 10271.146238,
'unrealised_profit': -10.628408369648495}
Alpha = 0.001
#price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.rolling(20).mean() # Ordinary moving average
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0,log=False)
trade_value = 300
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 10:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < 10:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2d = e
(stragey_2d.df['total']/e.initial_balance).plot(figsize=(17,6),grid = True);
그 결과는 직선 위로, BNB는 단지 약간의 윙과 윙을 가져옵니다, 낮은 Adjust_value는 모든 변동을 포착합니다. 처리 수수료가 없으면 이익이 훌륭합니다.
만약 조정값이 작다면 어떻게 될까요?
Alpha = 0.001
#price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.rolling(20).mean() # Ordinary moving average
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 300
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 10:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < 10:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2e = e
(stragey_2e.df['total']/e.initial_balance).plot(figsize=(17,6),grid = True);
그 결과, 그것은 또한 직선 하향 곡선에서 나왔다. 당신이 그것에 대해 생각하면 쉽게 이해할 수 있습니다, 작은 스프레드 내에서 빈번한 조정은 처리 수수료를 잃게 할 것입니다.
전체적으로, 수수료 수준이 낮을수록, Adjust_value가 설정될 수 있는 크기가 작아질수록, 거래가 더 자주 이루어지고, 이익이 더 높습니다.
알파 설정에 문제가 있습니다
분 줄이 있기 때문에 기준값은 1분마다 한 번 업데이트 됩니다. 여기서 우리는 단순히 알파의 크기를 결정하기 위해 백테스트를 합니다. 현재 권장 알파 설정은 0.001입니다.
for Alpha in [0.0001, 0.0003, 0.0006, 0.001, 0.0015, 0.002, 0.004, 0.01, 0.02]:
#price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.rolling(20).mean() # Ordinary moving average
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() #Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 300
for row in price_usdt.iloc[-7500:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 0.5*trade_value:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < -0.5*trade_value:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
print(Alpha, e.account['USDT']['unrealised_profit']+e.account['USDT']['realised_profit'])
0.0001 -77.80281760941007
0.0003 179.38803796199724
0.0006 218.12579924541367
0.001 271.1462377177959
0.0015 250.0014065973528
0.002 207.38692166891275
0.004 129.08021828803027
0.01 65.12410041648158
0.02 58.62356792410955
마지막으로, 오랜 시간 백테스트의 결과를 살펴보십시오. 지금, 하나에 이어 다른 상승, 그리고 오늘의 순자산은 새로운 최저 수준입니다. 다음 확신을 줄 수 있습니다. 분 줄의 빈도가 높기 때문에, 그것은 시간 내에 포지션을 열고 닫을 것입니다. 따라서 이익은 훨씬 더 높을 것입니다.
또 다른 점은, 우리는 항상 고정 트레이드_밸류를 사용했는데, 이는 후기 기간에 자금의 활용을 불충분하게 만들고, 실제 수익률은 여전히 많이 증가할 수 있습니다.
2개월의 백테스트 기간은 어떻게 될까요?
Alpha = 0.001
#price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.rolling(20).mean() # Ordinary moving average
price_usdt_btc_norm2 = price_usdt_btc/price_usdt_btc.ewm(alpha=Alpha).mean() # Here is consistent with the strategy, using EMA
trade_symbols = list(set(symbols))
price_usdt_btc_norm_mean = price_usdt_btc_norm2[trade_symbols].mean(axis=1)
e = Exchange(trade_symbols,initial_balance=10000,commission=0.00075,log=False)
trade_value = 300
for row in price_usdt.iloc[:].iterrows():
e.Update(row[0], row[1])
for symbol in trade_symbols:
price = row[1][symbol]
if np.isnan(price):
continue
diff = price_usdt_btc_norm2.loc[row[0],symbol] - price_usdt_btc_norm_mean[row[0]]
aim_value = -trade_value*round(diff/0.01,1)
now_value = e.account[symbol]['value']*np.sign(e.account[symbol]['amount'])
if aim_value - now_value > 0.5*trade_value:
e.Buy(symbol, price, round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
if aim_value - now_value < -0.5*trade_value:
e.Sell(symbol, price, -round((aim_value - now_value)/price, 6),round(e.account[symbol]['realised_profit']+e.account[symbol]['unrealised_profit'],2))
stragey_2f = e
(stragey_2f.df['total']/stragey_2e.initial_balance).plot(figsize=(17,6),grid = True);
(stragey_2f.df['leverage']/stragey_2e.initial_balance).plot(figsize=(17,6),grid = True);