पिछले लेख में, हमने एक साथ एक सरल हेजिंग रणनीति लागू की, और फिर हम सीखेंगे कि इस रणनीति को कैसे अपग्रेड किया जाए। रणनीतिक परिवर्तन बड़े नहीं हैं, लेकिन परिवर्तनों के विवरणों पर ध्यान देने की आवश्यकता है। कोड में कुछ स्थानों की परिभाषाएं पिछले लोगों से बदल गई हैं, जिन्हें समझने की आवश्यकता है।
A exchange -> B exchange
, B exchange -> A exchange
, और क्षैतिज रेखा है कि फैलाव को ट्रिगर करता है ड्राइंग. हम का उपयोगline drawing class library
सीधे निपटने के लिए, लाभ यह है कि यह उपयोग करने के लिए आसान है, यहाँ हम भी सीखते हैं कि कैसे उपयोग करने के लिएtemplate class library
एफएमजेड का कार्य।इसके बाद, आइए इन डिजाइनों को एक-एक करके लागू करें।
उदाहरण के रूप में Binance स्पॉट असली बॉट ले लो, स्पॉट लीवरेज मोड पर स्विच, कोड का उपयोग करेंexchanges[i].IO
, पैरामीटर दर्ज करेंtrade_normal
लीवरेज पोजीशन पर पोजीशन के आधार पर स्विच करना और इनपुटtrade_super_margin
पूर्ण स्थिति में लेवरेज स्विच करने के लिए, बैकटेस्टिंग समर्थित नहीं है. यह केवल वास्तविक बॉट में प्रयोग किया जाता है.
तैयारी के चरण में जोड़ेंmain
कार्य:
// Switch leverage mode
for (var i = 0 ; i < exchanges.length ; i++) { // Traverse and detect all added exchange objects
if (exchanges[i].GetName() == "Binance" && marginType != 0) { //If the exchange object represented by the current i-index is Binance spot, and the parameter marginType of the strategy interface is not the option of "common currency", execute the switch operation
if (marginType == 1) {
Log(exchanges[i].GetName(), "Set to leveraged position-by-position")
exchanges[i].IO("trade_normal")
} else if (marginType == 2) {
Log(exchanges[i].GetName(), "Set to leveraged full position")
exchanges[i].IO("trade_super_margin")
}
}
}
यहाँ की रणनीति केवल Binance स्पॉट के सिक्का-से-सिक्का लीवरेज मोड को स्विच करने के लिए कोड जोड़ती है, इसलिए रणनीति मापदंडों पर स्विच सेटिंग केवल Binance स्पॉट के लिए मान्य है।
यह पहले से ही लिपटे ड्राइंग टेम्पलेट का उपयोग करने के लिए बहुत आसान है. टेम्पलेट का नाम हम उपयोग कर रहे हैंLine Drawing Library
इसे सीधे एफएमजेड प्लेटफार्म रणनीति वर्ग पर खोजकर प्राप्त किया जा सकता है।
या सीधे लिंक पर क्लिक करेंःhttps://www.fmz.com/strategy/27293इस टेम्पलेट के लिए प्रतिलिपि पृष्ठ पर कूदने के लिए.
इस टेम्पलेट क्लास लाइब्रेरी को अपनी रणनीति लाइब्रेरी में कॉपी करने के लिए बटन पर क्लिक करें.
फिर आप रणनीति संपादन पृष्ठ पर टेम्पलेट कॉलम में उपयोग करने के लिए टेम्पलेट क्लास लाइब्रेरी की जांच कर सकते हैं. इसे जांचने के बाद रणनीति को सहेजें, और रणनीति इस टेम्पलेट को संदर्भित करेगी. यह केवल टेम्पलेट क्लास लाइब्रेरी के उपयोग का एक संक्षिप्त विवरण है. इस रणनीति ने पहले ही इस टेम्पलेट का संदर्भ दिया है, इसलिए ऑपरेशन को दोहराने की आवश्यकता नहीं है. जब आप इस रणनीति को रणनीति वर्ग में कॉपी करते हैं, तो आप देख सकते हैं किLine Drawing Library
रणनीति संपादन पृष्ठ पर टेम्पलेट बार में संदर्भित किया गया है।
हम मुख्य रूप से सीखेंगे किLine Drawing Library
एक चार्ट तैयार करने के लिए।
हम का प्रसार आकर्षित करने की योजना बना रहे हैंA->B
, के प्रसारB->A
, और फैलाव के ट्रिगर लाइन. हम दो वक्र (वर्तमान A से B, B से A फैलाव), दो क्षैतिज रेखाओं (ट्रिगर फैलाव लाइन), ऊपर के चित्र में दिखाया गया है के रूप में आकर्षित करने की जरूरत है।
क्योंकि हम एकतरफा हेजिंग डिजाइन करना चाहते हैं, के ट्रिगर लाइनोंA->B
औरB->A
हम पिछले लेख में डिजाइन का उपयोग नहीं कर सकते।
पिछले लेख में
var targetDiffPrice = hedgeDiffPrice
if (diffAsPercentage) {
targetDiffPrice = (depthA.Bids[0].Price + depthB.Asks[0].Price + depthB.Bids[0].Price + depthA.Asks[0].Price) / 4 * hedgeDiffPercentage
}
वहाँ केवल एक ट्रिगर फैलाव हैtargetDiffPrice
.
तो यहाँ हम कोड को बदलने के लिए है, पैरामीटर पहले बदलने के लिए.
फिर कोड को संशोधित करेंः
var targetDiffPriceA2B = hedgeDiffPriceA2B
var targetDiffPriceB2A = hedgeDiffPriceB2A
if (diffAsPercentage) {
targetDiffPriceA2B = (depthA.Bids[0].Price + depthB.Asks[0].Price + depthB.Bids[0].Price + depthA.Asks[0].Price) / 4 * hedgeDiffPercentageA2B
targetDiffPriceB2A = (depthA.Bids[0].Price + depthB.Asks[0].Price + depthB.Bids[0].Price + depthA.Asks[0].Price) / 4 * hedgeDiffPercentageB2A
}
इस तरह, अंतर ट्रिगर लाइन पिछले से बदल गया हैtargetDiffPrice
दो सेtargetDiffPriceA2B
, targetDiffPriceB2A
.
अगला कदम रेखा रेखांकन पुस्तकालय के रेखा रेखा फ़ंक्शन का उपयोग करके चार्ट पर इन आंकड़ों को आकर्षित करना है।
// drawing
$.PlotHLine(targetDiffPriceA2B, "A->B") // The first parameter of this function is the value of the horizontal line in the Y-axis direction, and the second parameter is the display text
$.PlotHLine(targetDiffPriceB2A, "B->A")
जब रणनीति चल रही है, वहाँ इस तरह एक चार्ट है.
इसके बाद वास्तविक समय में प्रसार वक्र खींचें, रेखा को ओवरड्राइव करने से बचने के लिए। संतुलन जाँच में वास्तविक समय में प्रसार डेटा की वक्र खींचने वाला कोड डालें।
if (ts - lastKeepBalanceTS > keepBalanceCyc * 1000) {
nowAccs = _C(updateAccs, exchanges)
var isBalance = keepBalance(initAccs, nowAccs, [depthA, depthB])
cancelAll()
if (isBalance) {
lastKeepBalanceTS = ts
if (isTrade) {
var nowBalance = _.reduce(nowAccs, function(sumBalance, acc) {return sumBalance + acc.Balance}, 0)
var initBalance = _.reduce(initAccs, function(sumBalance, acc) {return sumBalance + acc.Balance}, 0)
LogProfit(nowBalance - initBalance, nowBalance, initBalance, nowAccs)
isTrade = false
}
}
$.PlotLine("A2B", depthA.Bids[0].Price - depthB.Asks[0].Price) // Draw real-time spread curves
$.PlotLine("B2A", depthB.Bids[0].Price - depthA.Asks[0].Price) // The first parameter is the name of the curve, and the second parameter is the value of the curve at the current moment, that is, the value in the Y-axis direction at the current moment
}
इस प्रकार, ड्राइंग कोड केवल 4 पंक्तियों का है, जिससे रणनीति को रनटाइम पर एक ग्राफ प्रदर्शित किया जा सकता है।
जैसा कि ऊपर उल्लेख किया गया है, स्प्रेड ट्रिगर लाइन को दो में संशोधित किया गया है, जो हेजिंग ट्रिगर को नियंत्रित करता हैA->B
औरB->A
इस प्रकार, पिछले आदेश मूल्य एल्गोरिथ्म का उपयोग नहीं किया जा सकता है, और इसके बजाय बाजार मूल्य में स्लिप मूल्य जोड़ने की विधि का उपयोग किया जाता है।
if (depthA.Bids[0].Price - depthB.Asks[0].Price > targetDiffPriceA2B && Math.min(depthA.Bids[0].Amount, depthB.Asks[0].Amount) >= minHedgeAmount) { // A -> B market conditions are met
var priceSell = depthA.Bids[0].Price - slidePrice
var priceBuy = depthB.Asks[0].Price + slidePrice
var amount = Math.min(depthA.Bids[0].Amount, depthB.Asks[0].Amount)
if (nowAccs[0].Stocks > minHedgeAmount && nowAccs[1].Balance * 0.8 / priceSell > minHedgeAmount) {
amount = Math.min(amount, nowAccs[0].Stocks, nowAccs[1].Balance * 0.8 / priceSell, maxHedgeAmount)
Log("trigger A->B:", depthA.Bids[0].Price - depthB.Asks[0].Price, priceBuy, priceSell, amount, nowAccs[1].Balance * 0.8 / priceSell, nowAccs[0].Stocks) // Tips
hedge(exB, exA, priceBuy, priceSell, amount)
cancelAll()
lastKeepBalanceTS = 0
isTrade = true
}
} else if (depthB.Bids[0].Price - depthA.Asks[0].Price > targetDiffPriceB2A && Math.min(depthB.Bids[0].Amount, depthA.Asks[0].Amount) >= minHedgeAmount) { // B -> A market conditions are met
var priceBuy = depthA.Asks[0].Price + slidePrice
var priceSell = depthB.Bids[0].Price - slidePrice
var amount = Math.min(depthB.Bids[0].Amount, depthA.Asks[0].Amount)
if (nowAccs[1].Stocks > minHedgeAmount && nowAccs[0].Balance * 0.8 / priceBuy > minHedgeAmount) {
amount = Math.min(amount, nowAccs[1].Stocks, nowAccs[0].Balance * 0.8 / priceBuy, maxHedgeAmount)
Log("trigger B->A:", depthB.Bids[0].Price - depthA.Asks[0].Price, priceBuy, priceSell, amount, nowAccs[0].Balance * 0.8 / priceBuy, nowAccs[1].Stocks) //Tips
hedge(exA, exB, priceBuy, priceSell, amount)
cancelAll()
lastKeepBalanceTS = 0
isTrade = true
}
}
चूंकि खरीद और बिक्री की कीमतों को दो आंकड़ों में अलग किया जाता है, इसलिए हेजिंग फ़ंक्शनhedge
इसे भी संशोधित करने की आवश्यकता है।
function hedge(buyEx, sellEx, priceBuy, priceSell, amount) {
var buyRoutine = buyEx.Go("Buy", priceBuy, amount)
var sellRoutine = sellEx.Go("Sell", priceSell, amount)
Sleep(500)
buyRoutine.wait()
sellRoutine.wait()
}
इन परिवर्तनों के आधार पर कुछ मामूली समायोजन भी हैं, जिन्हें यहाँ दोहराया नहीं जाएगा। विवरण के लिए आप कोड देख सकते हैं।
रणनीति के लिए बातचीत जोड़ें, ताकि रणनीति वास्तविक समय में प्रसार ट्रिगर लाइन को संशोधित कर सके। यह एक अर्ध-स्वचालित रणनीति की डिजाइन आवश्यकता है, जिसे यहां एक शिक्षण प्रदर्शन के रूप में भी लागू किया गया है। रणनीति बातचीत डिजाइन भी बहुत सरल है. सबसे पहले, रणनीति संपादन पृष्ठ पर रणनीति के लिए बातचीत नियंत्रण जोड़ें.
जोड़ा दो नियंत्रण, एक कहा जाता है A2B और एक कहा जाता है B2A. नियंत्रण इनपुट बॉक्स में एक मूल्य दर्ज करने के बाद, इनपुट बॉक्स के दाईं ओर बटन पर क्लिक करें. एक निर्देश तुरंत रणनीति के लिए भेजा जाएगा, उदाहरण के लिएः मान दर्ज करें123
इनपुट बॉक्स में, क्लिक करेंA2B
बटन, और एक निर्देश तुरंत रणनीति के लिए भेजा जाएगा.
A2B:123
रणनीति कोड में इंटरैक्टिव डिटेक्शन और प्रोसेसिंग कोड डिजाइन करें।
// interact
var cmd = GetCommand() // Every time the loop is executed here, it checks whether there is an interactive command, and returns to an empty string if not.
if (cmd) { // An interactive command was detected, such as A2B:123
Log("command received:", cmd)
var arr = cmd.split(":") // Split out the interactive control name and the value in the input box, arr[0] is A2B, arr[1] is 123
if (arr[0] == "A2B") { // Determine whether the triggered interactive control is A2B
Log("Modify the parameters of A2B, ", diffAsPercentage ? "The parameter is the difference percentage" : "The parameter is the difference:", arr[1])
if (diffAsPercentage) {
hedgeDiffPercentageB2A = parseFloat(arr[1]) // Modify the trigger spread line
} else {
hedgeDiffPriceA2B = parseFloat(arr[1]) // Modify the trigger spread line
}
} else if (arr[0] == "B2A") { // Triggered control detected is B2A
Log("Modify the parameters of B2A, ", diffAsPercentage ? "The parameter is the difference percentage" : "The parameter is the difference:", arr[1])
if (diffAsPercentage) {
hedgeDiffPercentageA2B = parseFloat(arr[1])
} else {
hedgeDiffPriceB2A = parseFloat(arr[1])
}
}
}
स्थिति पट्टी डेटा को अधिक व्यवस्थित और देखने में आसान बनाएं।
var tbl = {
"type" : "table",
"title" : "data",
"cols" : ["exchange", "coin", "freeze coin", "denominated currency", "freeze denominated currency", "trigger spread", "current spread"],
"rows" : [],
}
tbl.rows.push(["A:" + exA.GetName(), nowAccs[0].Stocks, nowAccs[0].FrozenStocks, nowAccs[0].Balance, nowAccs[0].FrozenBalance, "A->B:" + targetDiffPriceA2B, "A->B:" + (depthA.Bids[0].Price - depthB.Asks[0].Price)])
tbl.rows.push(["B:" + exB.GetName(), nowAccs[1].Stocks, nowAccs[1].FrozenStocks, nowAccs[1].Balance, nowAccs[1].FrozenBalance, "B->A:" + targetDiffPriceB2A, "B->A:" + (depthB.Bids[0].Price - depthA.Asks[0].Price)])
LogStatus(_D(), "\n", "`" + JSON.stringify(tbl) + "`")
बैकटेस्टिंग केवल एक परीक्षण रणनीति है, एक प्रारंभिक पता लगाने का कार्य है, और कई कीड़े वास्तव में बैकटेस्टिंग चरण में परीक्षण किए जा सकते हैं। बैकटेस्टिंग परिणामों पर बहुत अधिक ध्यान देने की आवश्यकता नहीं है। अंतिम रणनीति को अभी भी वास्तविक वातावरण में परीक्षण करने की आवश्यकता है।
रणनीति स्रोत कोडःhttps://www.fmz.com/strategy/302834