.3, Grenzwert=3)
Wenn nicht, barstate.ishistory und schließen < offen
Strategie.Abbrechen
Strategie.Abbrechen ((
---------------------------
6. ```strategy.cancel_all```
The ```strategy.cancel_all``` function is similar to the ```strategy.cancel``` function. It can cancel/stop all pre-listed commands. The ```when``` parameter can be specified.
Parameters:
- ```when```: Execution conditions.
```pine
/*backtest
start: 2022-07-03 00:00:00
end: 2022-07-09 00:00:00
period: 1d
basePeriod: 1h
exchanges: [{"eid":"Binance","currency":"BTC_USDT"}]
*/
strategy("strategy.cancel Demo", pyramiding=3)
var isStop = false
if isStop
runtime.error("stop")
strategy.entry("long1", strategy.long, 0.1, limit=1)
strategy.entry("long2", strategy.long, 0.2, limit=2)
strategy.entry("long3", strategy.long, 0.3, limit=3)
if not barstate.ishistory and close < open
strategy.cancel_all()
isStop := true
strategy.order
Die Funktionalität und Parameter-Einstellungen vonstrategy.order
Die Funktionen derstrategy.entry
Der Unterschied besteht darin, dass diestrategy.order
die Funktion nicht beeinträchtigt wirdpyramiding
Parameter-Einstellungen derstrategy
Funktion, und es gibt keine Bestellzählgrenze.
Parameter:
id
: Es kann verstanden werden, dass eine Handelsposition einen Namen für die Referenzierung erhält.direction
: Wenn die Bestellrichtung lang ist (kaufen), geben Sie die eingebaute Variable einstrategy.long
, und wenn Sie kurz gehen wollen (verkaufen), geben Sie die Variablestrategy.short
.qty
: Geben Sie den zu platzierenden Auftragsbetrag an, wenn dieser Parameter nicht übergeben wird, wird der Standardbetrag der Aufträge verwendet.when
: Ausführungsbedingung, Sie können diesen Parameter angeben, um zu kontrollieren, ob diese aktuelle Auftragsoperation ausgelöst wird oder nicht.limit
: Geben Sie den Auftragsbegrenzungspreis an.stop
Stop-Loss-Preis.Wir werden die Funktion verwenden, diestrategy.order
Die Zahl der Bestellungen ist unbegrenzt.strategy.exit
die bedingte Exit-Funktion, um ein Skript zu konstruieren, das dem Grid-Trading ähnelt.
/*backtest
start: 2021-03-01 00:00:00
end: 2022-08-30 00:00:00
period: 1d
basePeriod: 1h
exchanges: [{"eid":"Binance","currency":"ETH_USDT"}]
args: [["ZPrecision",0,358374]]
*/
varip beginPrice = -1
if not barstate.ishistory
if beginPrice == -1 or (math.abs(close - beginPrice) > 1000 and strategy.opentrades == 0)
beginPrice := close
for i = 0 to 20
strategy.order("buy"+i, strategy.long, 0.01, limit=beginPrice-i*200, when=(beginPrice-i*200)<close)
strategy.exit("coverBuy"+i, "buy"+i, qty=0.01, profit=200)
strategy.order("sell"+i, strategy.short, 0.01, limit=beginPrice+i*200, when=(beginPrice+i*200)>close)
strategy.exit("coverSell"+i, "sell"+i, qty=0.01, profit=200)
Die Strategienbeispiele in diesem Tutorial dienen nur zu Lehrzwecken, um Strategiedesign-Ideen zu leiten, und nicht für Handelsleitlinien oder -Ratschläge.
strategy("supertrend", overlay=true)
[supertrend, direction] = ta.supertrend(input(5, "factor"), input.int(10, "atrPeriod"))
plot(direction < 0 ? supertrend : na, "Up direction", color = color.green, style=plot.style_linebr)
plot(direction > 0 ? supertrend : na, "Down direction", color = color.red, style=plot.style_linebr)
if direction < 0
if supertrend > supertrend[2]
strategy.entry("entry long", strategy.long)
else if strategy.position_size < 0
strategy.close_all()
else if direction > 0
if supertrend < supertrend[3]
strategy.entry("entry short", strategy.short)
else if strategy.position_size > 0
strategy.close_all()
Es ist sehr einfach, eine Trendstrategie zu schreiben, indem man die Pine-Sprache verwendet, und hier werden wir eine einfache Trend-Folge-Strategie mit einem Super-Trend-Indikator entwerfen.
Erstens beginnt der Strategie-Code mit einigen einfachen Einstellungen.strategy
Funktion:strategy("supertrend", overlay=true)``, which just sets a strategy title "supertrend". The
Überlagerungparameter is set to
- Das stimmt., so that the drawn indicator lines and other content are displayed on the main chart. The first thing we need to look at when designing a Pine strategy or learning a Pine strategy script is the strategy interface parameter design. Let's look at the source code of the ''supertrend indicator strategy'', which has the
Input ` ` Funktion, die wir im vorherigen Kurs gelernt haben
[Supertrend, Richtung] = ta.Supertrend ((Eingabe ((5,
Faktor input.int(10,), atPeriode ))
Dieinput
Funktionsaufruf wird als Parameter direkt an dieta.supertrend
Indikatorfunktion zur Berechnung des Supertrend-Indikators.
Standardmäßig gibt die Funktion zwei Parametersteuerungen auf dem Strategiebildschirm der Pine-Sprache an, wie unten gezeigt:
Wie wir sehen können, ist der Standardwert der Steuerung der erste Parameter derinput
Funktion undinput
Funktionsreihe (hier istinput.int
Mit diesen beiden Funktionen können wir dann die Parameter desta.supertrend
Die Funktion wird auf dem Strategiebildschirm angezeigt.supertrend
Funktion berechnet Preisdatensupertrend
und eine Richtung Datendirection
Dann benutzen wir dieplot
Die Funktion, um ein Diagramm zu zeichnen, beachten Sie, dass bei der Zeichnung des Diagramms, es basiert auf der Richtung des Supertrend-Indikators, nur die aktuelle Richtung gezeichnet wird.direction
ist -1, ist die aktuelle Marktentwicklung aufwärts, wenndirection
Wir können also sehen, dass die aktuelle Marktentwicklung nach unten geht.plot
Funktion zieht das Diagramm, wenn das Urteildirection
ist größer oder kleiner als 0.
Der nächsteif... else if
Logik ist das Urteil des Handelssignals.direction < 0
Der Markt ist im Aufwärtstrend.supertrend
der Preis des Supertrend-Indikators auf den beiden vorherigen BARs (d. h.supertrend[2], remember that the historical operator refers to the historical data of a variable
Wenn es eine aktuelle Position gibt, wird die Umkehrorderfunktion zuerst die vorherige Position schließen und dann die Position nach der aktuellen Handelsrichtung öffnen.supertrend > supertrend[2]
Die Kommission ist der Auffassung, daß diestrategy.position_size < 0
Wenn Sie kurzfristige Positionen halten, wird es auslösenstrategy.close_all()
Ausführung der Funktion zum Schließen aller Positionen.
direction > 0
Wenn es lange Positionen gibt, werden alle Positionen geschlossen, und dann, wenn die Bedingungsupertrend < supertrend[3]
Wird ein kurzes Signal ausgelöst.[3]
Der Preisindikator ist in der Regel auf der dritten BAR der vorangegangenen Nummer zu verweisen. Das kurzfristige Risiko ist in einigen Märkten, wie dem Markt für den Vertragshandel, schließlich etwas höher als das lange Risiko.
Fürta.supertrend
Ich möchte Sie fragen, ob jemand daran interessiert ist, wie man beurteilt, ob der aktuelle Trend aufwärts oder abwärts ist?
In der Tat kann dieser Indikator auch in Form von benutzerdefinierten Funktionen in der Pine-Sprache implementiert werden:
pine_supertrend(factor, atrPeriod) =>
src = hl2
atr = ta.atr(atrPeriod)
upperBand = src + factor * atr
lowerBand = src - factor * atr
prevLowerBand = nz(lowerBand[1])
prevUpperBand = nz(upperBand[1])
lowerBand := lowerBand > prevLowerBand or close[1] < prevLowerBand ? lowerBand : prevLowerBand
upperBand := upperBand < prevUpperBand or close[1] > prevUpperBand ? upperBand : prevUpperBand
int direction = na
float superTrend = na
prevSuperTrend = superTrend[1]
if na(atr[1])
direction := 1
else if prevSuperTrend == prevUpperBand
direction := close > upperBand ? -1 : 1
else
direction := close < lowerBand ? 1 : -1
superTrend := direction == -1 ? lowerBand : upperBand
[superTrend, direction]
Diese benutzerdefinierte Funktion ist genau der gleiche Algorithmus wie die eingebaute Funktionta.supertrend
, und natürlich sind auch die berechneten Indikatordaten genau die gleichen.
Wie wir aus diesem benutzerdefinierten Funktionsalgorithmus sehen können, wird Pinehl2
In diesem Fall wird die ATR-Wertung (Volatilität) für einen bestimmten Zeitraum auf der Grundlage des Parameters atrPeriod berechnet.
AktualisierunglowerBand
undupperBand
nach den dreifachen Ausdrücken im Code.
lowerBand := lowerBand > prevLowerBand or close[1] < prevLowerBand ? lowerBand : prevLowerBand
upperBand := upperBand < prevUpperBand or close[1] > prevUpperBand ? upperBand : prevUpperBand
lowerBand: lowerBand, verwendet, um festzustellen, ob sich der Aufwärtstrend geändert hat. upperBand: upperBand, verwendet, um festzustellen, ob sich der Abwärtstrend geändert hat. lowerBand und upperBand werden immer berechnet, nur die aktuelle Trendrichtung wird am Ende dieser benutzerdefinierten Funktion bestimmt.
else if prevSuperTrend == prevUpperBand
direction := close > upperBand ? -1 : 1
else
direction := close < lowerBand ? 1 : -1
Hier wird beurteilt, dass, wenn der Preiswert des letzten BAR auf dem SupertrendprevUpperBand
, d. h. das obere Band, bedeutet, daß der Strom einen Abwärtstrend zeigt.close
überschreitet dieupperBand
Bei einem Preisdurchbruch gilt der Trend als zu diesem Zeitpunkt verschoben und in einen Aufwärtstrend umgewandelt.direction
Das ist der Grund, warum man in der Super-Trend-Strategie sieht, dass ein Super-Trend-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategie-Strategieif direction < 0
Wenn die Signalbedingung ausgelöst wird, um lang zu gehen.direction > 0
, wird die Signalbedingung ausgelöst, um kurz zu gehen.
superTrend := direction == -1 ? lowerBand : upperBand
[superTrend, direction]
Schließlich werden spezifische Preisdaten und Richtungsdaten des Super Trend Indicators auf der Grundlage der Richtungswahl zurückgegeben.
/*backtest
start: 2021-03-01 00:00:00
end: 2022-09-08 00:00:00
period: 1h
basePeriod: 15m
exchanges: [{"eid":"Binance","currency":"ETH_USDT"}]
args: [["v_input_1",4374],["v_input_2",3],["v_input_3",300],["ZPrecision",0,358374]]
*/
varip balance = input(50000, "balance")
varip stocks = input(0, "stocks")
maxDiffValue = input(1000, "maxDiffValue")
if balance - close * stocks > maxDiffValue and not barstate.ishistory
// more balance , open long
tradeAmount = (balance - close * stocks) / 2 / close
strategy.order("long", strategy.long, tradeAmount)
balance := balance - tradeAmount * close
stocks := stocks + tradeAmount
runtime.log("balance:", balance, ", stocks:", stocks, ", tradeAmount:", tradeAmount)
else if close * stocks - balance > maxDiffValue and not barstate.ishistory
// more stocks , open short
tradeAmount = (close * stocks - balance) / 2 / close
strategy.order("short", strategy.short, tradeAmount)
balance := balance + tradeAmount * close
stocks := stocks - tradeAmount
runtime.log("balance:", balance, ", stocks:", stocks, ", tradeAmount:", tradeAmount)
plot(balance, title="balance value(quoteCurrency)", color=color.red)
plot(stocks*close, title="stocks value(quoteCurrency)", color=color.blue)
Wir werden nun einige Beispiele für Strategieentwicklung in der Pine-Sprache weiterlesen, diesmal werden wir eine dynamische Balance-Strategie lernen.BaseCurrency
und der Betrag vonQuoteCurrency
. Je nachdem, welcher Vermögenswert relative Preis steigt, steigt der Wert, der im Konto gehalten wird, und der Vermögenswert wird verkauft. Wenn der relative Preis eines Vermögenswerts sinkt, sinkt der Wert, der im Konto gehalten wird, und der Vermögenswert wird gekauft. Dies wird als dynamische Ausgleichsstrategie bezeichnet. In der Tat ist die dynamische Ausgleichsstrategie eine Art Gitterstrategie, die in oszillierenden Märkten gut funktioniert. Aber im Trendmarkt wird es weiterhin Geld verlieren, wir müssen warten, bis der Preis zurückkehrt, um Verluste langsam zum Gewinn zu reduzieren, aber der Vorteil ist, dass die dynamische Ausgleichsstrategie immer den oszillierenden Trend des Marktes erfassen kann.
Der Nachteil, wie auf dem Backtest-Diagramm dieser Strategie gezeigt, ist, dass die Strategie einen großen schwimmenden Verlust während der Phase des allgemeinen Preistrends nach oben (oder unten) hat.
Schauen wir uns das Strategie-Code-Design an:
Wir verwenden ein vereinfachtes Design, das einebalance
(d. h. Anzahl der QuoteCurrency-Vermögenswerte) undstocks
Wir lesen nicht die tatsächliche Anzahl der Vermögenswerte auf dem Konto, sondern verwenden einfach den simulierten Betrag, um die entsprechenden Käufe und Verkäufe zu berechnen.maxDiffValue
, das das Beurteilungskriterium für die Durchführung des Ausgleichs darstellt.BaseCurrency
undQuoteCurrency
überschreitetmaxDiffValue
Wird der Ausgleichsprozess stattfinden, indem der Vermögenswert zu einem hohen Preis verkauft und der Vermögenswert zu einem niedrigen Preis gekauft wird, um den Vermögenswert auszugleichen?
Die Strategie-Trading-Signal-Trigger muss in der Echtzeit BAR-Phase sein, so dass, wenn die Urteile in der Strategie-Trading-Bedingungen mitnot barstate.ishistory
. Kaufen, wenn diebalance
Wert überschreitet diestocks
Der Verkauf wird nach der Abwicklung der Handelsrechnung durch den Verkaufsbetreiber erfolgt.balance
undstocks
Die Variablen werden aktualisiert und warten dann auf den nächsten Auslöser.
Die obigen Informationen der Strategie Backtest enthält den Preis der Art zum Zeitpunkt des Beginns der Strategie Backtest, der Preis ist 1458, so dass ich den Parameterbalance
zu: 4374 (1458*3) absichtlich den Parameter setzenstocks
3. Lassen Sie den Vermögenswert im Gleichgewicht anfangen.
In den vorangegangenen Kursen haben wir über diestrategy.exit
In diesem Strategie-Design-Beispiel verwenden wir die Positionsausgang-Funktion, von der wir kein Beispiel hatten, um die Tracking-Stop- und Take-Profit-Funktion zu erklären.strategy.exit
Funktion zur Optimierung einer Super-Trend-Strategie.
Zunächst wollen wir uns die Stop-Loss- und Take-Profit-Parameter derstrategy.exit
Funktion:
trail_price
: Die Position, die die logische Aktion auslöst, einen Tracking-Stop-Loss- und einen Stop-Loss-Close-Auftrag zu platzieren (an der durch den Preis angegebenen Position).trail_offset
: Der Abstand zum höchsten (bei Long) oder niedrigsten (bei Short) Preis einer geschlossenen Position, die nach der Ausführung einer Tracking-Stop-Loss- und Take-Profit-Aktion platziert wurde.trail_points
Wie dietrail_price
Parameter, mit der Ausnahme, dass er Gewinnpunkte als die angegebene Position nimmt.Ist das nicht leicht zu verstehen? Es spielt keine Rolle! Lassen Sie uns ein Strategie-Backtest-Szenario durchgehen, um zu verstehen, was eigentlich ziemlich einfach ist.
/*backtest
start: 2022-09-23 00:00:00
end: 2022-09-23 08:00:00
period: 1m
basePeriod: 1m
exchanges: [{"eid":"Binance","currency":"ETH_USDT"}]
args: [["RunMode",1,358374],["ZPrecision",0,358374]]
*/
strategy("test", overlay = true)
varip a = na
varip highPrice = na
varip isTrade = false
varip offset = 30
if not barstate.ishistory and not isTrade
strategy.entry("test 1", strategy.long, 1)
strategy.exit("exit 1", "test 1", 1, trail_price=close+offset, trail_offset=offset)
a := close + offset
runtime.log("the price per point is:", syminfo.mintick, ", current close:", close)
isTrade := true
if close > a and not barstate.ishistory
highPrice := na(highPrice) ? close : highPrice
highPrice := close > highPrice ? close : highPrice
plot(a, "trail_price trigger line")
plot(strategy.position_size>0 ? highPrice : na, "current highest price")
plot(strategy.position_size>0 ? highPrice-syminfo.mintick*offset : na, "moving stop trigger line")
Sofortiger Long-Eintrag, wenn die Strategie beginnt, um auszuführen, und dann sofort platziert einestrategy.exit
Ausgangsauftrag (es spezifizierte die Tracking-Stop-Loss- und Take-Profit-Parameter), wenn der Preis der Marktänderung über die Trail_Price-Trigger-Linie stieg, begann die Implementierung der Trailing-Stop-Loss- und Take-Profit-Logik, Stop-Loss und Take-Profit-Linie (blau), der höchsten Preisdynamik anzupassen, die blaue Linie Position ist der Stop-Loss und Take-Profit-Trigger, um die Position zu schließen, und schließlich, wenn der Marktpreis unter die blaue Linie fällt, die den Schluss der Position auslöst.
Dann verwenden wir diese Funktion, um eine Super-Trending-Strategie zu optimieren, wir einfach einestrategy.exit
Der Exitplan-Auftrag wird dem Strategie-Eintrittsbefehl hinzugefügt, um dieses Verzögerungs-Stop-Loss- und Take-Profit-Feature hinzuzufügen.
if not barstate.ishistory and findOrderIdx("open") >= 0 and state == 1
trail_price := strategy.position_size > 0 ? close + offset : close - offset
strategy.exit("exit", "open", 1, trail_price=trail_price, trail_offset=offset)
runtime.log("the price per point is:", syminfo.mintick, ", current close:", close, ",trail_price:", trail_price)
state := 2
tradeBarIndex := bar_index
Vollständiger Strategiecode:
/*backtest
start: 2022-05-01 00:00:00
end: 2022-09-27 00:00:00
period: 1d
basePeriod: 5m
exchanges: [{"eid":"Binance","currency":"ETH_USDT"}]
args: [["RunMode",1,358374],["ZPrecision",0,358374]]
*/
varip trail_price = na
varip offset = input(50, "offset")
varip tradeBarIndex = 0
// 0 : idle , 1 current_open , 2 current_close
varip state = 0
findOrderIdx(idx) =>
ret = -1
if strategy.opentrades == 0
ret
else
for i = 0 to strategy.opentrades - 1
if strategy.opentrades.entry_id(i) == idx
ret := i
break
ret
if strategy.position_size == 0
trail_price := na
state := 0
[superTrendPrice, dir] = ta.supertrend(input(2, "atr coefficient"), input(20, "atr period"))
if ((dir[1] < 0 and dir[2] > 0) or (superTrendPrice[1] > superTrendPrice[2])) and state == 0 and tradeBarIndex != bar_index
strategy.entry("open", strategy.long, 1)
state := 1
else if ((dir[1] > 0 and dir[2] < 0) or (superTrendPrice[1] < superTrendPrice[2])) and state == 0 and tradeBarIndex != bar_index
strategy.entry("open", strategy.short, 1)
state := 1
// Reverse signal, close all positions
if strategy.position_size > 0 and dir[2] < 0 and dir[1] > 0
strategy.cancel_all()
strategy.close_all()
runtime.log("trend reversal, long positions all closed")
else if strategy.position_size < 0 and dir[2] > 0 and dir[1] < 0
strategy.cancel_all()
strategy.close_all()
runtime.log("trend reversal, short positions all closed")
if not barstate.ishistory and findOrderIdx("open") >= 0 and state == 1
trail_price := strategy.position_size > 0 ? close + offset : close - offset
strategy.exit("exit", "open", 1, trail_price=trail_price, trail_offset=offset)
runtime.log("the price per point is:", syminfo.mintick, ", current close:", close, ", trail_price:", trail_price)
state := 2
tradeBarIndex := bar_index
plot(superTrendPrice, "superTrendPrice", color=dir>0 ? color.red : color.green, overlay=true)