
dydx_v4, हाइपरलिक्विड, वर्टेक्स और एवो सहित कई DEX एक्सचेंजों को FMZ पर एनकैप्सुलेट और कनेक्ट किया गया है। जैसे-जैसे केंद्रीकृत एक्सचेंजों में मूल्य अंतरण के लिए प्रतिस्पर्धा बढ़ती जा रही है, कई मात्रात्मक व्यापारियों ने अपना ध्यान विकेंद्रीकृत एक्सचेंजों की ओर मोड़ लिया है। इस लेख में, हम DEX और CEX के बीच मूल्य अंतर निगरानी के डिजाइन और कार्यान्वयन पर चर्चा करेंगे।
हेजिंग आर्बिट्रेज रणनीति का पहला चरण लक्ष्य पोर्टफोलियो के मूल्य अंतर की गणना करना और यह देखना और विश्लेषण करना है कि क्या कोई ट्रेडिंग अवसर मौजूद है। इसलिए, मूल्य अंतर निगरानी रणनीति को डिजाइन करना और लागू करना पहला बुनियादी कार्य है। हमारी डिजाइन आवश्यकताएँ हैं:
कोड 200 पंक्तियों से कम है, और इसका डिज़ाइन किया गया कार्य केवल विभिन्न एक्सचेंजों में किसी निश्चित उत्पाद के वास्तविक समय मूल्य अंतर की गणना करना है। जब रणनीति शुरू में चलाई जाती है, तो रणनीति के लिए कॉन्फ़िगर किए गए सभी एक्सचेंज ऑब्जेक्ट्स को DEX समूह और CEX समूह में वर्गीकृत किया जाएगा। प्रत्येक पोल FMZ प्लेटफॉर्म द्वारा समाहित बहु-थ्रेडेड फ़ंक्शन थ्रेड के माध्यम से किया जाता है, और साथ ही REST इंटरफ़ेस का अनुरोध करता है: ऑर्डर बुक इंटरफ़ेसGetDepth, आवश्यक किस्मों की अनुरोधित खरीद आदेश सूची और बिक्री आदेश सूची डेटा रिकॉर्ड करें। फिर, DEX समूह और CEX समूह को एक अंतर संयोजन (DEX-CEX संयोजन, यानी, आर्बिट्रेज जोड़ी) में संयोजित किया जाता है, और मूल्य अंतर की गणना की जाती है।
विनिमय प्रकार का निर्धारण: आरंभीकरण के दौरान, जोड़े गए एक्सचेंज ऑब्जेक्ट का मूल्यांकन यह निर्धारित करने के लिए किया जाएगा कि यह स्पॉट है या फ्यूचर्स।
विभिन्न एक्सचेंजों में किसी निश्चित अंतर्निहित परिसंपत्ति के लिए अलग-अलग नाम हो सकते हैं, इसलिए उत्पाद के नाम को समायोजित करने की आवश्यकता होती है:
कार्यक्रम को विभिन्न एक्सचेंजों के प्रतीकों के नामकरण नियमों के अनुसार समायोजित करने की आवश्यकता है। उदाहरण के लिए, वर्टेक्स अनुबंधों के व्यापारिक जोड़ों का नाम इस प्रकार है:XXX_USD, जो वास्तव में यूएसडीसी पर आधारित एक सतत अनुबंध है। वर्टेक्स के स्पॉट में ETH का नाम WETH है।
परिशुद्धता प्राप्त करें: आरंभीकरण के दौरान, संपूर्ण बाजार जानकारी प्राप्त की जाती है। अनुरोधित विशिष्ट प्रतीक के अनुसार, बाद के डेटा परिशुद्धता प्रसंस्करण कार्यों के लिए संबंधित परिशुद्धता की जांच की जा सकती है।
जानकारी मांगना सभी गहन डेटा प्राप्त होने से पहले, प्रोग्राम प्रतीक्षा करेगा और जांचता रहेगा कि क्या ऐसे एक्सचेंज हैं जिनका डेटा अपडेट नहीं किया गया है। यदि डेटा प्राप्त नहीं हुआ है, तो प्रोग्राम 100 मिलीसेकंड के लिए निष्क्रिय हो जाएगा। अनुरोधित ऑर्डर बुक डेटा threading.Dict() (समवर्ती थ्रेड्स के साथ इंटरेक्शन के लिए उपयोग किया जाता है) द्वारा बनाए गए ऑब्जेक्ट में रिकॉर्ड किया जाता है, और प्रत्येक पोल के अंत में डेटा रीसेट किया जाता है।
संक्षेप यह रणनीति कार्यान्वयन दिखाता है कि वास्तविक समय में विभिन्न एक्सचेंजों में मूल्य अंतर की निगरानी कैसे की जाए तथा संभावित मध्यस्थता अवसरों की गणना कैसे की जाए। उचित प्रतीक सुधार, गहन डेटा कैप्चर, सटीक नियंत्रण और बहु-थ्रेडेड ऑपरेशन के माध्यम से, सिस्टम वास्तविक समय मूल्य अंतर की कुशलतापूर्वक निगरानी कर सकता है। रणनीति सीखने वालों के लिए, इस कोड के कार्यान्वयन विचारों को समझने से उन्हें यह समझने में मदद मिल सकती है कि लेनदेन डेटा प्राप्त करने के लिए एपीआई का उपयोग कैसे करें, कई एक्सचेंजों से डेटा कैसे संसाधित करें, लेनदेन प्रसार की गणना और आउटपुट कैसे करें, और इन तकनीकों को वास्तविक लेनदेन में कैसे लागू करें।
let symbolList = []
function createEx(idx, exs) {
let self = {}
let cexEidList = ["Binance", "Bybit", "Futures_Binance", "Futures_Bybit"]
let dexEidList = ["Vertex", "Hyperliquid", "Futures_Hyperliquid", "Futures_Vertex"]
self.name = exs[idx].GetName()
self.idx = idx
self.e = exs[idx]
self.depths = threading.Dict()
self.markets = self.e.GetMarkets()
if (!self.markets) {
throw "GetMarkets error"
}
if (dexEidList.includes(self.name)) {
self.type = "DEX"
} else if (cexEidList.includes(self.name)) {
self.type = "CEX"
} else {
throw "not support " + self.name
}
if (self.name.startsWith("Futures_")) {
self.isFutures = true
} else {
self.isFutures = false
}
self.correctSymbol = function(symbol) {
if (self.name == "Vertex") {
let correctList = {"BTC_USDC": "WBTC_USDC", "ETH_USDC": "WETH_USDC"}
if (typeof(correctList[symbol]) != "undefined") {
return correctList[symbol]
}
} else if (self.name == "Hyperliquid") {
let correctList = {"BTC_USDC": "UBTC_USDC"}
if (typeof(correctList[symbol]) != "undefined") {
return correctList[symbol]
}
} else if (self.name == "Futures_Hyperliquid") {
return symbol.replace("_USDC", "_USD")
}
return symbol
}
self.reqDepth = function(symbol) {
symbol = self.correctSymbol(symbol)
threading.Thread(function(idx, symbol, threadingDict) {
let depth = exchanges[idx].GetDepth(symbol)
if (depth) {
threadingDict.set(symbol, depth)
} else {
threadingDict.set(symbol, null)
}
}, self.idx, symbol, self.depths)
}
self.getPrecision = function(symbol) {
symbol = self.correctSymbol(symbol)
let marketInfo = self.markets[symbol]
if (marketInfo) {
return [marketInfo.PricePrecision, marketInfo.AmountPrecision]
} else {
return [8, 8]
}
}
self.init = function() {
self.depths = threading.Dict()
}
self.getDepth = function(symbol) {
symbol = self.correctSymbol(symbol)
return self.depths.get(symbol)
}
return self
}
function createManager(symbolList, exs) {
let self = {}
self.symbolList = symbolList
self.exchanges = []
self.hedgePair = []
self.initHedgePair = function () {
for (let i in exs) {
let ex = createEx(i, exs)
self.exchanges.push(ex)
}
let arrDEX = self.exchanges.filter(item => item.type == "DEX")
let arrCEX = self.exchanges.filter(item => item.type == "CEX")
for (let dex of arrDEX) {
for (let cex of arrCEX) {
self.hedgePair.push({"dex": dex, "cex": cex})
}
}
}
self.calcHedgeData = function () {
let beginTimestamp = new Date().getTime()
for (let e of self.exchanges) {
for (let symbol of self.symbolList) {
e.reqDepth(symbol)
}
}
while (true) {
let isWait = false
for (let e of self.exchanges) {
for (let symbol of self.symbolList) {
let depth = e.getDepth(symbol)
if (depth == null || typeof(depth) == "undefined") {
isWait = true
}
}
}
if (isWait) {
Sleep(100)
} else {
break
}
}
let tbls = []
for (let symbol of self.symbolList) {
let tbl = {"type": "table", "title": symbol + "差价", "cols": ["pair", "bid-ask", "ask-bid", "dex ask", "dex bid", "cex ask", "cex bid"], "rows": []}
for (let p of self.hedgePair) {
let dex = p["dex"]
let cex = p["cex"]
let pricePrecision = Math.max(dex.getPrecision(symbol)[0], cex.getPrecision(symbol)[0])
let dexDepth = dex.getDepth(symbol)
let cexDepth = cex.getDepth(symbol)
if (dexDepth && cexDepth) {
p["bid-ask"] = _N(dexDepth.Bids[0].Price - cexDepth.Asks[0].Price, pricePrecision)
p["ask-bid"] = _N(dexDepth.Asks[0].Price - cexDepth.Bids[0].Price, pricePrecision)
// 输出信息、观察测试
Log(dex.name, cex.name, symbol, "bid-ask:", p["bid-ask"], ", ask-bid", p["ask-bid"])
p[dex.name + "-ask"] = dexDepth.Asks[0].Price + "/" + dexDepth.Asks[0].Amount
p[dex.name + "-bid"] = dexDepth.Bids[0].Price + "/" + dexDepth.Bids[0].Amount
p[cex.name + "-ask"] = cexDepth.Asks[0].Price + "/" + cexDepth.Asks[0].Amount
p[cex.name + "-bid"] = cexDepth.Bids[0].Price + "/" + cexDepth.Bids[0].Amount
} else {
p["bid-ask"] = "--"
p["ask-bid"] = "--"
p[dex.name + "-ask"] = "--"
p[dex.name + "-bid"] = "--"
p[cex.name + "-ask"] = "--"
p[cex.name + "-bid"] = "--"
}
let pairName = dex.name + "-" + cex.name
tbl["rows"].push([pairName, p["bid-ask"], p["ask-bid"], p[dex.name + "-ask"], p[dex.name + "-bid"], p[cex.name + "-ask"], p[cex.name + "-bid"]])
}
tbls.push(tbl)
}
for (let e of self.exchanges) {
e.init()
}
let endTimestamp = new Date().getTime()
return [tbls, (endTimestamp - beginTimestamp) + "毫秒"]
}
self.initHedgePair()
return self
}
function main() {
LogReset(1)
let loopCount = 0
symbolList = strSymbolList.split(",")
let m = createManager(symbolList, exchanges)
while (true) {
let ret = m.calcHedgeData()
loopCount++
LogStatus(_D(), "耗时:", ret[1], ", 轮询次数:", loopCount, "\n", "`" + JSON.stringify(ret[0]) + "`")
Sleep(1000)
}
}
पैरामीटर डिज़ाइन:

स्पॉट उत्पाद की निगरानी करें:

दो प्रकार की निगरानी करें:

विस्तार दिशा:
FMZ प्लेटफॉर्म विकेन्द्रीकृत एक्सचेंजों (DEX) और विकेन्द्रीकृत वित्त (DeFi) के लिए अपने तकनीकी समर्थन को बढ़ाना जारी रखेगा, और कार्यों और उत्पादों को लगातार दोहराएगा और अपडेट करेगा।
पढ़ने के लिए आपका शुक्रिया।