리소스 로딩... 로딩...

동전 고리량 거래는 새로운 것 같네요 -- 동전 고리량화 (Quantitative Coin Ringing) 에 대해 더 자세히 알아보세요.

저자:발명가들의 수량화 - 작은 꿈, 2021-05-28 09:50:12, 2021-09-21 21:06:08에 업데이트되었습니다.

img

동전 고리량 거래 새게 보아도 가 당신을 동전 고리량에 가깝게 데려다줍니다.

이전 기사에서는 간단한 격자 전략의 거래 논리 분석을 설명했고, 이 기사에서는 이 교육 전략의 설계를 완성했습니다.

  • 거래 논리 분석 이전 기사에서 우리는 매트리스의 각 매트리스 라인을 가로질러 현재 가격을 판단하면 매트리스 라인을 통과하면 거래 동작을 유발할 수 있다고 말했습니다. 그러나 실제로는 논리 세부 사항이 많으며 종종 전략을 이해하지 못하는 신입생들이 쉽게 잘못된 인식을 형성 할 수 있습니다.

    먼저 우리가 고려해야 할 첫 번째 세부 사항은 무한의 디자인입니다.createNet그렇다면? 이 함수는 제한된 수의 격자 라인들로 이루어진 격자 데이터 구조를 생성한다. 그렇다면 만약 전략이 실행될 때 가격이 이 격자 데이터 구조의 경계를 넘어선다면 (최고의 가장 높은 가격, 최하위의 가장 낮은 가격) 그래서 우리는 먼저 그레이드 데이터 구조에 확장 장치를 추가해야 합니다.

    메인 함수를 작성하기 시작합니다. 메인 함수는 정책 실행을 시작하는 코드입니다.

    var diff = 50                                 // 全局变量,网格间距,可以设计成参数,方便讲解,我们把这个参数写死在代码里。
    function main() {
        // 实盘开始运行后,从这里开始执行策略代码
        var ticker = _C(exchange.GetTicker)       // 获取市场最新的行情数据ticker,ticker这个数据的结构参看FMZ API文档:https://www.fmz.com/api#ticker
        var net = createNet(ticker.Last, diff)    // 我们上篇设计的初始构造网格数据结构的函数,这里构造一个网格数据结构net
    
        while (true) {                            // 然后程序逻辑就进入了这个while死循环,策略执行到此将不停的循环执行这里{}符号之内的代码
            ticker = _C(exchange.GetTicker)       // 死循环代码部分的第一行,获取最新的行情数据,更新给ticker变量
            // 检查网格范围
            while (ticker.Last >= net[net.length - 1].price) {
                net.push({
                    buy : false,
                    sell : false,
                    price : net[net.length - 1].price + diff,
                })
            }
            while (ticker.Last <= net[0].price) {
                var price = net[0].price - diff
                if (price <= 0) {
                    break
                }
                net.unshift({
                    buy : false,
                    sell : false,
                    price : price,
                })
            }
            
            // 还有其它代码...
        }
    }
    

    그레이드 데이터 구조를 확장할 수 있는 것은 이 코드 (위 코드에서 선택):

          // 检查网格范围
          while (ticker.Last >= net[net.length - 1].price) {   // 如果价格超过网格最高价格的网格线
              net.push({                                       // 就在网格最高价格的网格线之后加入一个新的网格线
                  buy : false,                                 // 初始化卖出标记
                  sell : false,                                // 初始化买入标记
                  price : net[net.length - 1].price + diff,    // 在之前最高价格的基础上再加一个网格间距
              })
          }
          while (ticker.Last <= net[0].price) {                // 如果价格低于网格最低价格的网格线
              var price = net[0].price - diff                  // 区别于向上添加,要注意向下添加新网格线的价格不能小于等于0,所以这里要判断
              if (price <= 0) {                                // 小于等于0就不添加了,跳出这层循环
                  break
              }
              net.unshift({                                    // 就在网格最低价格的网格线之前添加一个新的网格线
                  buy : false,
                  sell : false,
                  price : price,
              })
          }
    

    다음으로 트레이드 트리거를 구체적으로 구현하는 방법을 고려해야 합니다.

    var diff = 50
    var amount = 0.002       // 增加一个全局变量,也可以设计成参数,当然为了简便讲解,我们也写死在策略代码,
                             // 这个参数控制每次网格线上触发交易时的交易量
    function main() {
        var ticker = _C(exchange.GetTicker)
        var net = createNet(ticker.Last, diff)
        var preTicker = ticker       // 在主循环(死循环)开始前,设置一个变量,记录上一次的行情数据
        while (true) {
            ticker = _C(exchange.GetTicker)
            // 检查网格范围
            while (ticker.Last >= net[net.length - 1].price) {
                net.push({
                    buy : false,
                    sell : false,
                    price : net[net.length - 1].price + diff,
                })
            }
            while (ticker.Last <= net[0].price) {
                var price = net[0].price - diff
                if (price <= 0) {
                    break
                }
                net.unshift({
                    buy : false,
                    sell : false,
                    price : price,
                })
            }  
    
            // 检索网格
            for (var i = 0 ; i < net.length ; i++) {     // 遍历网格数据结构中的所有网格线
                var p = net[i]
                if (preTicker.Last < p.price && ticker.Last > p.price) {         // 上穿,卖出,当前节点已经交易过不论SELL BUY ,都不再交易
                    if (i != 0) {
                        var downP = net[i - 1]
                        if (downP.buy) {
                            exchange.Sell(-1, amount, ticker)
                            downP.buy = false 
                            p.sell = false 
                            continue
                        }
                    }
                    if (!p.sell && !p.buy) {
                        exchange.Sell(-1, amount, ticker)
                        p.sell = true
                    }
                } else if (preTicker.Last > p.price && ticker.Last < p.price) {  // 下穿,买入
                    if (i != net.length - 1) {
                        var upP = net[i + 1]
                        if (upP.sell) {
                            exchange.Buy(-1, amount * ticker.Last, ticker)
                            upP.sell = false 
                            p.buy = false 
                            continue
                        }
                    }
                    if (!p.buy && !p.sell) {
                        exchange.Buy(-1, amount * ticker.Last, ticker)
                        p.buy = true 
                    } 
                }
            }
            preTicker = ticker    // 把当前的行情数据记录在preTicker中,在下一次循环中,作为“上一次”行情数据和最新的对比,判断上穿下穿
            Sleep(500)
        }
    }  
    

    이 사진들은

    • : : :preTicker.Last < p.price && ticker.Last > p.price
    • 그라이트를 통과하는 조건은 다음과 같습니다:preTicker.Last > p.price && ticker.Last < p.price

    이 모든 것은 우리가 앞서 말한 것과 같습니다.

    img

    위아래로 이동하는 것은 거래를 할 수 있는지 여부를 판단하는 첫 번째 단계에 불과하며, 그레이드 데이터의 표시도 포함됩니다.

    만약 위를 입고 있다면, 현재 그리드 라인보다 낮은 가격을 판단하고 가장 최근의 그리드 라인에서의 구매 표시를 합니다. 만약 구매 표시의 값이 true라면, 이전 그리드 라인이 구매되었다는 것을 나타냅니다.

    방금의 조건을 판단한 후, 트리거가 없다면 판단을 계속합니다. 만약 현재 그리드 라인의 바이/셀 마크가 모두 거짓이라면, 현재 그리드 라인이 거래가 가능하다는 것을 의미합니다.

    이 모든 것은 다른 사람들이 생각하는 것과 같은 논리입니다.

전체 전략 재검토

이 함수에서 어떤 데이터를 볼 수 있도록showTbl데이터 표시.

function showTbl(arr) {
    var tbl = {
        type : "table", 
        title : "网格",
        cols : ["网格信息"],
        rows : []
    }
    var arrReverse = arr.slice(0).reverse()
    _.each(arrReverse, function(ele) {
        var color = ""
        if (ele.buy) {
            color = "#FF0000"
        } else if (ele.sell) {
            color = "#00FF00"
        }
        tbl.rows.push([JSON.stringify(ele) + color])
    })
    LogStatus(_D(), "\n`" + JSON.stringify(tbl) + "`", "\n 账户信息:", exchange.GetAccount())
}

전 전략 코드:

/*backtest
start: 2021-04-01 22:00:00
end: 2021-05-22 00:00:00
period: 1d
basePeriod: 1m
exchanges: [{"eid":"OKEX","currency":"ETH_USDT","balance":100000}]
*/

var diff = 50
var amount = 0.002
function createNet(begin, diff) {
    var oneSideNums = 10
    var up = []
    var down = []
    for (var i = 0 ; i < oneSideNums ; i++) {
        var upObj = {
            buy : false,
            sell : false, 
            price : begin + diff / 2 + i * diff,
        }
        up.push(upObj)

        var j = (oneSideNums - 1) - i
        var downObj = {
            buy : false,
            sell : false,
            price : begin - diff / 2 - j * diff,
        }
        if (downObj.price <= 0) {  // 价格不能小于等于0 
            continue
        }
        down.push(downObj)
    }

    return down.concat(up)
}

function showTbl(arr) {
    var tbl = {
        type : "table", 
        title : "网格",
        cols : ["网格信息"],
        rows : []
    }
    var arrReverse = arr.slice(0).reverse()
    _.each(arrReverse, function(ele) {
        var color = ""
        if (ele.buy) {
            color = "#FF0000"
        } else if (ele.sell) {
            color = "#00FF00"
        }
        tbl.rows.push([JSON.stringify(ele) + color])
    })
    LogStatus(_D(), "\n`" + JSON.stringify(tbl) + "`", "\n 账户信息:", exchange.GetAccount())
}

function main() {
    var ticker = _C(exchange.GetTicker)
    var net = createNet(ticker.Last, diff)
    var preTicker = ticker 
    while (true) {
        ticker = _C(exchange.GetTicker)
        // 检查网格范围
        while (ticker.Last >= net[net.length - 1].price) {
            net.push({
                buy : false,
                sell : false,
                price : net[net.length - 1].price + diff,
            })
        }
        while (ticker.Last <= net[0].price) {
            var price = net[0].price - diff
            if (price <= 0) {
                break
            }
            net.unshift({
                buy : false,
                sell : false,
                price : price,
            })
        }

        // 检索网格
        for (var i = 0 ; i < net.length ; i++) {
            var p = net[i]
            if (preTicker.Last < p.price && ticker.Last > p.price) {         // 上穿,卖出,当前节点已经交易过不论SELL BUY ,都不再交易
                if (i != 0) {
                    var downP = net[i - 1]
                    if (downP.buy) {
                        exchange.Sell(-1, amount, ticker)
                        downP.buy = false 
                        p.sell = false 
                        continue
                    }
                }
                if (!p.sell && !p.buy) {
                    exchange.Sell(-1, amount, ticker)
                    p.sell = true
                }
            } else if (preTicker.Last > p.price && ticker.Last < p.price) {  // 下穿,买入
                if (i != net.length - 1) {
                    var upP = net[i + 1]
                    if (upP.sell) {
                        exchange.Buy(-1, amount * ticker.Last, ticker)
                        upP.sell = false 
                        p.buy = false 
                        continue
                    }
                }
                if (!p.buy && !p.sell) {
                    exchange.Buy(-1, amount * ticker.Last, ticker)
                    p.buy = true 
                } 
            }
        }

        showTbl(net)
        preTicker = ticker 
        Sleep(500)
    }
}

이 글은 이쪽에서 읽었습니다.

img

img

img

이러한 네트워크 전략의 특징은 트렌드 시장에 직면했을 때 큰 부진이 발생할 수 있으며, 부진한 시장에서 수익이 회복 될 수 있다는 것을 알 수 있습니다. 따라서 격자 전략은 위험이 없는 것이 아니며 현장 전략은 여전히 평상시 고장난한 거리를 누워있을 수 있으며, 선물 계약 격자 전략은 더 위험하며 격자 매개 변수에 대해 보수적인 설정을 필요로합니다.


관련

더 많은

husr12345이것은 C++ 언어입니다.

토니233은 현재 가격보다 높은 을 밟아야 하는 것 아니겠습니까? 또한 exchange.Sell ((-1, amount, ticker) 이 함수가 API 문서에서와 어떻게 다르는지, 나는 API 문서에서 exchange.Sell ((Price, Amount) 이라고 적혀있는 것을 보았고, 왜 은 세 가지 매개 변수를 가지고 있습니까?

토니233정말 힘들어요.

위와 아래로 갈 때, exchange.Buy ((-1, amount * ticker.Last, ticker), amount* ticker.Last는 터무니없습니다.

CYZWXhttps://www.fmz.com/strategy/291160 last_tick = [] 선 = [] grid_buy_list = [] def netto ((now_price): 글로벌 라인 인쇄 (지금_값) 라인 = [now_price*(1+0.003*i) for i in range ((-1000,1000) ] 로그 (선) def ontick ((): 글로벌 마지막 틱 글로벌 라인 글로벌 grid_buy_list 계정 = 교환.GetAccount (() 틱어 = 교환.GetTicker() last_tick.append ((ticker['Last']) if len ((last_tick) == 1:귀환 elif len ((last_tick) == 100:del last_tick[0] 범위에 있는 i (선) 의 경우: if last_tick[-1] > line[i] and last_tick[-2] < line[i] and len(grid_buy_list)!= 0 and i > min(grid_buy_list) and account['Stocks'] >= 0.001: 교환.판매 (최후의 표지[-1],0.01) del grid_buy_list[grid_buy_list.index ((min(grid_buy_list)) ] 로그 (환송) elif last_tick[-1] < line[i] and last_tick[-2] > line[i] and i not in grid_buy_list: 교환.구입 (last_tick[-1],0.01) grid_buy_list.append (grid_buy_list.append)) 로그 (환송) def main ((): 네트 (환송.GetTicker) 로그 (환송) while(True): 틱 (tick)) 수면 (1000)

CYZWX드림 신 감사합니다, 매우 상세한 설명, 다시 구입하기 위해 설명, 마치 파이판을 작성 한 것처럼.

발명가들의 수량화 - 작은 꿈자바스크립트 (JavaScript) 언어의 전략입니다.

토니233이 글의 영구 계약은 선물로 간주되지 않습니까?

발명가들의 수량화 - 작은 꿈선물은 계약서 수이며 현시장 가격으로 지불하는 것은 금액입니다. 현시장 판매는 동전입니다.

토니233자, 또 다른 질문, 이 의 의미 ᅳ 참고: 거래소 아래 주문 인터페이스가 시장을 지원하는 목록 (< 아래 주문 유형을 지불할 때, 아래 주문량 매개 변수는 통화 단위 금액) ᅳ 디지털 화폐 선물 시장을 주문하는 방법, 아래 주문량 매개 변수는 계약 張数입니다. 나는 당신이이 게시물을 다시 테스트를 볼 수 있습니다okex의 et의usdt 영구 계약, 이것은 선물 시장을 주문하는 방법을 계산하지 않습니다? 아래 주문량 매개 변수는 이 계약이 아닙니다.

토니233오, 알았어

발명가들의 수량화 - 작은 꿈FMZ의 API 함수에서 로그 출력 함수를 생성할 수 있습니다. 예를 들어: Log ((...), exchange.Buy ((Price, Amount), exchange.CancelOrder ((Id) 등은 필요한 매개 변수 뒤에 추가된 출력 매개 변수와 함께 가능합니다. http://www.fmz.com/api#exchange.cancelorderid