7
Подписаться
276
Подписчики

Распространение логики стратегии арбитража разницы спотовых цен на нескольких биржах

Создано: 2022-06-27 21:26:27, Обновлено: 2024-12-02 21:35:44
comments   4
hits   7857

Распространение логики стратегии арбитража разницы спотовых цен на нескольких биржах

Стратегический принцип

Из-за ликвидности, когда на рынке происходит большой объем продаж или вытягивания, неизбежно будут большие колебания цен, и будет кратковременная разница в ценах между биржами. Стратегия заключается в том, чтобы ловить эти моменты и выполнять быстрые транзакции, чтобы завершить процесс покупки по низкой цене и продажи по высокой цене. Некоторые клиенты спрашивали меня, почему у меня так много бирж. Это неизбежно. Мы зарабатываем деньги на мгновенной разнице цен между биржами. Чем больше бирж, тем больше возможностей для разницы цен будет после кроссовера.

Основная логика стратегии
  1. Одновременное получение рыночной информации с нескольких бирж. Необходимо получать ее одновременно, чтобы сократить задержку получения рыночной информации. Для одновременного получения вы можете обратиться к плагину инструмента, которым я поделился.Плагин для одновременного обмена несколькими данными
  2. Объедините спрос и предложение всех бирж, чтобы получить объединенную информацию о котировках, где RealPrice — это цена после вычета комиссии за обработку.
function createOrders(depths, askOrders, bidOrders) {
    let asksIndex = 0;
    let bidIndex = 0;
    for (let i = 0; i < depths.length; i++) {
        let exchangeTariff = getExchangeTariff(i);
        let asks = depths[i].Asks;
        let bids = depths[i].Bids;
        for (let j = 0; j < Math.min(asks.length, bids.length, 20); j++) {
            if (asks[j].Amount >= minTakerAmount) {
                askOrders[asksIndex] = {
                    "Price": asks[j].Price,
                    "Amount": asks[j].Amount,
                    "Fee": asks[j].Price * exchangeTariff,
                    "RealPrice": asks[j].Price * (1 + exchangeTariff),
                    "Index": i,
                };
                asksIndex++;
            }
            if (bids[j].Amount >= minTakerAmount) {
                bidOrders[bidIndex] = {
                    "Price": bids[j].Price,
                    "Amount": bids[j].Amount,
                    "Fee": bids[j].Price * exchangeTariff,
                    "RealPrice": bids[j].Price * (1 - exchangeTariff),
                    "Index": i,
                };
                bidIndex++;
            }
        }
    }
    askOrders.sort(function (a, b) {
        return a.RealPrice - b.RealPrice;
    });
    bidOrders.sort(function (a, b) {
        return b.RealPrice - a.RealPrice;
    });
}
  1. Рассчитайте наиболее прибыльный арбитражный спред на основе объединенной рыночной информации. Поскольку мы принимаем заказы, то есть покупаем по самой низкой цене предложения и продаем по самой высокой цене предложения, пока bid.RealPrice > ask.RealPrice, есть пространство для прибыли.
function getArbitrageOrders(askOrders, bidOrders) {
    let ret = [];
    for (let i = 0; i < askOrders.length; i++) {
        for (let j = 0; j < bidOrders.length; j++) {
            let bidOrder = bidOrders[j];
            let askOrder = askOrders[i];
            if (bidOrder.Index === askOrder.Index) {
                continue
            }
            let minMigrateDiffPrice = ((askOrder.Price + bidOrder.Price) / 2 * minMigrateDiffPricePercent / 100);
            if (bidOrder.RealPrice - askOrder.RealPrice > minMigrateDiffPrice) {
                ret.push({
                    "Ask": askOrder,
                    "Bid": bidOrder,
                })
            }
        }
    }
    if (ret.length === 0) {
        ret.push({
            "Ask": askOrders[0],
            "Bid": bidOrders[0],
        });
    }
    //按最优价差排序
    ret.sort((a, b) => {
        return (b.Bid.RealPrice - b.Ask.RealPrice) - (a.Bid.RealPrice - a.Ask.RealPrice);
    });
    return ret;
}
  1. Теперь, когда мы получили информацию об арбитражном спреде на рынке, как нам решить, следует ли выполнять транзакцию и каким объемом торговать? Вот несколько ключевых моментов, которые следует учитывать:
  • Текущие оставшиеся активы
  • Размер спреда (если спред слишком мал, он будет только балансировать количество валюты, а если спред достаточно велик, он будет максимизировать количество транзакций)
  • Количество отложенных ордеров
    var askOrder = arbitrageOrder.Ask;
    var bidOrder = arbitrageOrder.Bid;
    var perAmountFee = arbitrageOrder.Ask.Fee + arbitrageOrder.Bid.Fee;
    var minRealDiffPrice = (askOrder.Price + bidOrder.Price) / 2 * minDiffPricePercent / 100;
    var minMigrateDiffPrice = ((askOrder.Price + bidOrder.Price) / 2 * minMigrateDiffPricePercent / 100);
    var curRealDiffPrice = arbitrageOrder.Bid.RealPrice - arbitrageOrder.Ask.RealPrice;
    var buyExchange = exchanges[arbitrageOrder.Ask.Index];
    var sellExchange = exchanges[arbitrageOrder.Bid.Index];
    var buySellAmount = 0;
    if (curRealDiffPrice > minRealDiffPrice) {
        buySellAmount = math.min(
            bidOrder.Amount,
            askOrder.Amount,
            maxTakerAmount,
            runningInfo.Accounts[bidOrder.Index].CurStocks,
            runningInfo.Accounts[askOrder.Index].CurBalance / askOrder.Price
        );
    } else if (bidOrder.Index !== askOrder.Index) {
        if (migrateCoinEx == -1) {
            if (curRealDiffPrice > minMigrateDiffPrice && runningInfo.Accounts[bidOrder.Index].CurStocks - runningInfo.Accounts[askOrder.Index].CurStocks > maxAmountDeviation) {
                buySellAmount = math.min(
                    bidOrder.Amount,
                    askOrder.Amount,
                    maxTakerAmount,
                    runningInfo.Accounts[bidOrder.Index].CurStocks,
                    runningInfo.Accounts[askOrder.Index].CurBalance / askOrder.Price,
                    runningInfo.Accounts[bidOrder.Index].CurStocks - ((runningInfo.Accounts[bidOrder.Index].CurStocks + runningInfo.Accounts[askOrder.Index].CurStocks) / 2)
                );
                if (buySellAmount >= minTakerAmount) {
                    Log("启动交易所平衡!");
                }
            }
        } else if (migrateCoinEx == askOrder.Index) {
            if (curRealDiffPrice > minMigrateDiffPrice && runningInfo.Accounts[bidOrder.Index].CurStocks > 0) {
                buySellAmount = math.min(
                    bidOrder.Amount,
                    askOrder.Amount,
                    maxTakerAmount,
                    runningInfo.Accounts[bidOrder.Index].CurStocks,
                    runningInfo.Accounts[askOrder.Index].CurBalance / askOrder.Price
                );
                if (buySellAmount >= minTakerAmount) {
                    Log("启动货币迁移:", exchanges[bidOrder.Index].GetName(), "-->", exchanges[askOrder.Index].GetName());
                }
            }
        }
    }
  1. После расчета количества ордеров транзакция может быть выполнена. Стратегия использует метод прямого добавления проскальзывания для принятия ордеров и размещения ордеров одновременно
            var buyWait = buyExchange.Go("Buy", _N(askOrder.Price * (1.01), pricePrecision), buySellAmount);
            var sellWait = sellExchange.Go("Sell", _N(bidOrder.Price * (0.99), pricePrecision), buySellAmount);
            var startWaitTime = new Date().getTime()
            Sleep(3000);
            var buyOrder = buyWait.wait()
            var sellOrder = sellWait.wait()
  1. Остается лишь логика расчета прибыли, обработка стоп-лоссов для невыполненных ордеров и т. д.
Фактические преимущества этой стратегии

Распространение логики стратегии арбитража разницы спотовых цен на нескольких биржах Распространение логики стратегии арбитража разницы спотовых цен на нескольких биржах Распространение логики стратегии арбитража разницы спотовых цен на нескольких биржах

Текущее отображение в реальном времени, основная логика остается неизменной, оптимизирована для поддержки нескольких валют

https://www.fmz.com/robot/464965

Наконец, добро пожаловать на биржу Laoqiu Quantitative Exchange: https://t.me/laoqiu_arbitrage