
dydx_v4, hyperliquid, vertex, এবং aevo সহ বেশ কিছু DEX এক্সচেঞ্জ FMZ-এ এনক্যাপসুলেট এবং সংযুক্ত করা হয়েছে। কেন্দ্রীভূত এক্সচেঞ্জগুলিতে মূল্য সালিসির প্রতিযোগিতা ক্রমশ তীব্র হয়ে উঠার সাথে সাথে, অনেক পরিমাণগত ব্যবসায়ী বিকেন্দ্রীভূত এক্সচেঞ্জের দিকে মনোনিবেশ করেছেন। এই প্রবন্ধে, আমরা DEX এবং CEX-এর মধ্যে মূল্য পার্থক্য পর্যবেক্ষণের নকশা এবং বাস্তবায়ন নিয়ে আলোচনা করব।
হেজিং আরবিট্রেজ কৌশলের প্রথম ধাপ হল লক্ষ্য পোর্টফোলিওর মূল্যের পার্থক্য গণনা করা এবং কোন ট্রেডিং সুযোগ আছে কিনা তা পর্যবেক্ষণ ও বিশ্লেষণ করা। অতএব, মূল্য পার্থক্য পর্যবেক্ষণ কৌশল ডিজাইন এবং বাস্তবায়ন করা হল প্রথম মৌলিক কাজ। আমাদের নকশার প্রয়োজনীয়তাগুলি হল:
কোডটি ২০০ লাইনেরও কম, এবং এর নকশা করা কাজটি শুধুমাত্র বিভিন্ন এক্সচেঞ্জে একটি নির্দিষ্ট পণ্যের রিয়েল-টাইম মূল্যের পার্থক্য গণনা করা। যখন কৌশলটি প্রাথমিকভাবে চালানো হবে, তখন কৌশলটির জন্য কনফিগার করা সমস্ত এক্সচেঞ্জ অবজেক্টগুলিকে DEX গ্রুপ এবং CEX গ্রুপে শ্রেণীবদ্ধ করা হবে। প্রতিটি পোল FMZ প্ল্যাটফর্ম দ্বারা এনক্যাপসুলেটেড মাল্টি-থ্রেডেড ফাংশন থ্রেডের মাধ্যমে সম্পাদিত হয় এবং একই সাথে REST ইন্টারফেস অনুরোধ করে: অর্ডার বুক ইন্টারফেসGetDepth, প্রয়োজনীয় জাতের অনুরোধকৃত ক্রয় আদেশ তালিকা এবং বিক্রয় আদেশ তালিকার তথ্য রেকর্ড করুন। তারপর, DEX গ্রুপ এবং CEX গ্রুপকে একটি পার্থক্য সংমিশ্রণে (DEX-CEX সংমিশ্রণ, অর্থাৎ, আরবিট্রেজ জোড়া) একত্রিত করা হয় এবং মূল্যের পার্থক্য গণনা করা হয়।
বিনিময়ের ধরণ নির্ধারণ: ইনিশিয়ালাইজেশনের সময়, যোগ করা এক্সচেঞ্জ অবজেক্টটি স্পট নাকি ফিউচার তা নির্ধারণ করার জন্য বিচার করা হবে।
বিভিন্ন এক্সচেঞ্জের একটি নির্দিষ্ট অন্তর্নিহিত সম্পদের জন্য বিভিন্ন নাম থাকতে পারে, তাই পণ্যের নাম সামঞ্জস্য করা প্রয়োজন:
বিভিন্ন এক্সচেঞ্জের প্রতীকের নামকরণের নিয়ম অনুসারে প্রোগ্রামটি সামঞ্জস্য করা প্রয়োজন। উদাহরণস্বরূপ, ভার্টেক্স চুক্তির ট্রেডিং জোড়াগুলির নামকরণ করা হয়েছে নিম্নরূপ:XXX_USD, যা আসলে USDC-এর উপর ভিত্তি করে একটি চিরস্থায়ী চুক্তি। ভার্টেক্সের স্থানে ETH এর নাম WETH।
নির্ভুলতা পান: প্রারম্ভিককরণের সময়, সম্পূর্ণ বাজার তথ্য প্রাপ্ত করা হয়। অনুরোধ করা নির্দিষ্ট প্রতীক অনুসারে, পরবর্তী ডেটা নির্ভুলতা প্রক্রিয়াকরণ ক্রিয়াকলাপের জন্য সংশ্লিষ্ট নির্ভুলতা জিজ্ঞাসা করা যেতে পারে।
ডেটা অনুরোধ সমস্ত গভীরতার তথ্য পাওয়ার আগে, প্রোগ্রামটি অপেক্ষা করবে এবং পরীক্ষা করবে যে এমন কোনও এক্সচেঞ্জ আছে কিনা যাদের ডেটা আপডেট করা হয়নি। যদি তথ্য প্রাপ্ত না করা হয়, তাহলে প্রোগ্রামটি ১০০ মিলিসেকেন্ডের জন্য স্লিপ করবে। অনুরোধকৃত অর্ডার বইয়ের ডেটা threading.Dict() (যৌথ থ্রেডের সাথে মিথস্ক্রিয়ার জন্য ব্যবহৃত) দ্বারা তৈরি একটি বস্তুতে রেকর্ড করা হয় এবং প্রতিটি পোলের শেষে ডেটা রিসেট করা হয়।
সারসংক্ষেপ এই কৌশল বাস্তবায়ন দেখায় কিভাবে রিয়েল টাইমে একাধিক এক্সচেঞ্জে মূল্যের পার্থক্য পর্যবেক্ষণ করা যায় এবং সম্ভাব্য সালিসি সুযোগ গণনা করা যায়। যুক্তিসঙ্গত প্রতীক সংশোধন, গভীর তথ্য ক্যাপচার, নির্ভুল নিয়ন্ত্রণ এবং মাল্টি-থ্রেডেড অপারেশনের মাধ্যমে, সিস্টেমটি দক্ষতার সাথে রিয়েল-টাইম মূল্যের পার্থক্য পর্যবেক্ষণ করতে পারে। কৌশল শিক্ষার্থীদের জন্য, এই কোডের বাস্তবায়নের ধারণাগুলি বোঝা তাদের লেনদেনের ডেটা পেতে API ব্যবহার করার পদ্ধতি, একাধিক এক্সচেঞ্জ থেকে ডেটা প্রক্রিয়াকরণ, লেনদেনের স্প্রেড গণনা এবং আউটপুট কীভাবে করতে হয় এবং প্রকৃত লেনদেনে এই প্রযুক্তিগুলি কীভাবে প্রয়োগ করতে হয় তা আয়ত্ত করতে সাহায্য করতে পারে।
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) এর জন্য তার প্রযুক্তিগত সহায়তা বৃদ্ধি করতে থাকবে এবং ক্রমাগত ফাংশন এবং পণ্যগুলির পুনরাবৃত্তি এবং আপডেট করবে।
পড়ার জন্য ধন্যবাদ।