Type/to search
8
Follow
1364
Followers
Apprenez étape par étape comment transformer une stratégie mono-produit Python en stratégie multi-produits
Discussions
Created 2020-01-20 17:33:36  Updated 2023-10-17 21:18:46
 14
 4783

img

1. Vous apprendre à transformer une stratégie mono-produit Python en une stratégie multi-produits

Dans l'article précédent, une stratégie Python très simple a été implémentée :« Version Python de la stratégie de poursuite à la hausse et de vente à la baisse »Cette stratégie permet d'exploiter un compte pour effectuer des transactions programmées sur une certaine paire de trading. Le principe est très simple, il consiste à chasser la hausse et à vendre la baisse. Parfois, nous souhaitons utiliser la même logique de trading pour exploiter différentes paires de trading. Vous pouvez créer plusieurs robots et définir différentes paires de trading pour trader différentes devises. Si la stratégie n’est pas très compliquée, compte tenu de la puissante flexibilité de la plateforme de trading quantitative de l’inventeur. Il est très facile de transformer une stratégie en une stratégie multi-produits, de sorte que vous pouvez exécuter plusieurs paires de trading en créant simplement un seul robot.

Le code source de la stratégie transformée :

'''backtest start: 2019-02-20 00:00:00 end: 2020-01-10 00:00:00 period: 1m exchanges: [{"eid":"OKEX","currency":"BTC_USDT"},{"eid":"OKEX","currency":"ETH_USDT","stocks":30},{"eid":"OKEX","currency":"LTC_USDT","stocks":100}] ''' import time import json params = { "arrBasePrice": [-1, -1, -1], # -1 "arrRatio": [0.05, 0.05, 0.05], # 0.05 "arrAcc": [], # _C(exchange.GetAccount) "arrLastCancelAll": [0, 0, 0], # 0 "arrMinStocks": [0.01, 0.01, 0.01], # 0.01 "arrPricePrecision": [2, 2, 2], # 2 "arrAmountPrecision": [3, 2, 2], # 2 "arrTick":[] } def CancelAll(e): while True : orders = _C(e.GetOrders) for i in range(len(orders)) : e.CancelOrder(orders[i]["Id"], orders[i]) if len(orders) == 0 : break Sleep(1000) def process(e, index): global params ticker = _C(e.GetTicker) params["arrTick"][index] = ticker if params["arrBasePrice"][index] == -1 : params["arrBasePrice"][index] = ticker.Last if ticker.Last - params["arrBasePrice"][index] > 0 and (ticker.Last - params["arrBasePrice"][index]) / params["arrBasePrice"][index] > params["arrRatio"][index]: params["arrAcc"][index] = _C(e.GetAccount) if params["arrAcc"][index].Balance * params["arrRatio"][index] / ticker.Last > params["arrMinStocks"][index]: e.Buy(ticker.Last, params["arrAcc"][index].Balance * params["arrRatio"][index] / ticker.Last) params["arrBasePrice"][index] = ticker.Last if ticker.Last - params["arrBasePrice"][index] < 0 and (params["arrBasePrice"][index] - ticker.Last) / params["arrBasePrice"][index] > params["arrRatio"][index]: params["arrAcc"][index] = _C(e.GetAccount) if params["arrAcc"][index].Stocks * params["arrRatio"][index] > params["arrMinStocks"][index]: e.Sell(ticker.Last, params["arrAcc"][index].Stocks * params["arrRatio"][index]) params["arrBasePrice"][index] = ticker.Last ts = time.time() if ts - params["arrLastCancelAll"][index] > 60 * 5 : CancelAll(e) params["arrLastCancelAll"][index] = ts def main(): global params for i in range(len(exchanges)) : params["arrAcc"].append(_C(exchanges[i].GetAccount)) params["arrTick"].append(_C(exchanges[i].GetTicker)) exchanges[i].SetPrecision(params["arrPricePrecision"][i], params["arrAmountPrecision"][i]) for key in params : if len(params[key]) < len(exchanges): raise "params error!" while True: tblAcc = { "type" : "table", "title": "account", "cols": ["账户信息"], "rows": [] } tblTick = { "type" : "table", "title": "ticker", "cols": ["行情信息"], "rows": [] } for i in range(len(exchanges)): process(exchanges[i], i) for i in range(len(exchanges)): tblAcc["rows"].append([json.dumps(params["arrAcc"][i])]) tblTick["rows"].append([json.dumps(params["arrTick"][i])]) LogStatus(_D(), "\n`" + json.dumps([tblAcc, tblTick]) + "`") Sleep(500)

2. Trouvez la différence

Comparez le code et constatez qu’il est très différent du code de l’article précédent ?
En fait, la logique de trading est exactement la même, sans aucun changement. C'est juste que nous avons changé la stratégie en plusieurs variantes, nous ne pouvons donc pas utiliser la forme précédente de « variable unique comme paramètre de stratégie ». Une solution plus raisonnable est pour créer le paramètre Array, l'index de chaque position dans le tableau correspond à la paire de trading ajoutée.

img

Ensuite, encapsulez le code logique de transaction dans une fonctionprocessDans la boucle principale de la stratégie, cette fonction est appelée de manière itérative en fonction des paires de trading ajoutées, de sorte que le code logique de trading est exécuté une fois pour chaque paire de trading.

  • Appel d'itération (parcours) :

    for i in range(len(exchanges)): process(exchanges[i], i)
  • Paramètres de la stratégie :

    params = { "arrBasePrice": [-1, -1, -1], # -1 "arrRatio": [0.05, 0.05, 0.05], # 0.05 "arrAcc": [], # _C(exchange.GetAccount) "arrLastCancelAll": [0, 0, 0], # 0 "arrMinStocks": [0.01, 0.01, 0.01], # 0.01 "arrPricePrecision": [2, 2, 2], # 2 "arrAmountPrecision": [3, 2, 2], # 2 "arrTick":[] }

    Cette conception permet à chaque paire de trading d'avoir ses propres paramètres, car les prix de chaque paire de trading peuvent varier considérablement et les paramètres peuvent également différer, des paramètres parfois différenciés sont donc nécessaires.

  • Fonction AnnulerTout

    Vous pouvez comparer les changements de cette fonction. Cette fonction modifie simplement un petit peu de code, puis réfléchissez à l'intention de cette modification.

  • Données du graphique à barres d'état

    Des graphiques ont été ajoutés pour afficher les données de marché et les données d'actifs du compte dans la barre d'état, afin que les actifs et les données de marché correspondant à chaque objet d'échange puissent être affichés en temps réel.

Après avoir maîtrisé les idées de conception ci-dessus, n’est-il pas très facile de modifier une stratégie Python en une stratégie multi-variété ?

3. Backtesting

img

img

img

La stratégie est fournie à titre indicatif uniquement, pour les backtests et les tests. Si vous êtes intéressé, vous pouvez l'optimiser et la mettre à niveau.
Adresse de la politique

Related Recommendations
Comment
All comments (14)

    孟总,请问为什么,你这个策略下单不用设置exchange.SetDirection("buy")方向,还有个e. 不是exchange.吗,我最近在学习策略

    4 years ago

    这个策略最低本金是多少啊

    6 years ago

    没有实盘过,该策略为教学策略,学习为主,可以自行修改、扩展、优化跑实盘。

    6 years ago

    怎么不交易啊,半天没有反应。。。。。

    6 years ago

    好了,好了,弄好了,我弄成币本位了,怪不得呢

    6 years ago

    img 现在好了,但是我账户里是有钱的,你这个策略最少本金要投入多少啊,是不是我账户里的钱不够

    6 years ago

    可以具体看下这个策略源码, 策略公开的,策略逻辑很简单就是追涨杀跌。注意,这个是个数字货币现货策略,不能跑期货,可以自己修改成期货的。

    6 years ago

    img 是添加的托管者IP啊,没错啊

    6 years ago

    GetAccount: 400: {"error_message":"Invalid IP","code":30011,"error_code":"30011","message":"Invalid IP"}
    IP我也添加到API里面了,怎么还是出错

    6 years ago

    申请API KEY 的时候,设置的IP地址是允许访问的白名单地址,你设置了以后,就只有这个IP地址可以使用你的API KEY访问API接口。你设置的是你的托管者的IP地址么?

    6 years ago

    img 这个怎么解决

    6 years ago

    托管者所在服务器安装一下python。

    6 years ago

    机器人K线周期设置多少

    6 years ago

    这个策略不看K线的, 随便设置都行,回测的话因为影响tick粒度,设置为1分钟。

    6 years ago
  • 1
iPhone Download
Forums
PINE Language
© 2015 - ∞ INVENTOR PTE LTD (SG)