Stratégie de filtrage multiple par canal gaussien : comment créer un système de trading quantitatif robuste

GAUSSIAN Kijun-Sen VAPI ATR TRAILING
Date de création: 2025-09-02 18:22:32 Dernière modification: 2025-09-09 09:39:46
Copier: 0 Nombre de clics: 333
2
Suivre
319
Abonnés

Stratégie de filtrage multiple par canal gaussien : comment créer un système de trading quantitatif robuste Stratégie de filtrage multiple par canal gaussien : comment créer un système de trading quantitatif robuste

Pourquoi les indicateurs technologiques traditionnels échouent-ils dans des marchés complexes ?

Dans le domaine du trading quantitatif, nous sommes souvent confrontés à un problème central: un seul indicateur technique est susceptible de générer de faux signaux dans le bruit du marché, ce qui entraîne des arrêts fréquents et des retraits de fonds. Alors, comment construire un système de trading qui capte les tendances tout en filtrant efficacement le bruit ?

La stratégie de filtrage multiple du canal de Gauss analysée aujourd’hui, nous offre une solution qui mérite d’être étudiée en profondeur, en combinant habilement quatre indicateurs techniques de différentes dimensions.

L’architecture technologique de base: comment fonctionnent les quatre filtres ?

1. Gaussian Channel - Le cœur de la reconnaissance des tendances

Le fondement de la stratégie est un filtre de Gauss à 4 niveaux avec une fenêtre d’échantillonnage de 144 cycles. Contrairement aux moyennes mobiles traditionnelles, le filtre de Gauss élimine une grande partie du bruit du marché grâce à une modélisation mathématique, tout en conservant une sensibilité aux variations de prix.

Paramètres clés:

  • Nombre de pôles de Gauss: 4
  • Cycle d’échantillonnage: 144 (capture des tendances à moyen terme)
  • Multiplication des ondes de filtration: 1,414 (multiplication par écart standard, pour contrôler la largeur du canal)

2. Ligne Kijun-Sen ((130 cycles) - Confirmation de la tendance à moyen et long terme

La ligne de Kijun-Sen à 130 cycles est utilisée comme filtre de tendance au lieu des traditionnels 26 cycles.

Les réglages de périodes plus longues permettent:

  • Réduction des signaux de fausse détection
  • S’assurer que la direction des transactions est conforme à la tendance dominante
  • Améliorer la qualité des signaux et réduire la fréquence des transactions

3. Indicateur VAPI - analyse des prix et des volumes de livraison

VAPI (Volume Adjusted Price Indicator) permet d’évaluer les intentions réelles des acteurs du marché en analysant la relation entre le volume d’opérations et les variations de prix. Lorsque VAPI est supérieur à 0, le support est supérieur à 0, et lorsque le support est inférieur à 0, le support est inférieur à 0.

4. Arrêt dynamique de l’ATR - Mécanisme de contrôle des risques

En utilisant 4,5 fois l’ATR de 11 cycles comme distance de stop, ce réglage prend en compte la volatilité du marché et évite des stops trop serrés déclenchés par le bruit du marché.

L’innovation dans la gestion des fonds: la sagesse d’une stratégie de fractionnement 7525

La meilleure chose à apprendre de cette stratégie est sa manière unique de gérer les fonds:

Logistique de dépôt:

  • 75% de la position: 3,5 fois plus de risques fixes que le rendement du stop loss
  • 25% de la position: arrêt de suivi dynamique

Pourquoi cette conception ?

  1. Assurer le revenu de baseLe blocage fixe des positions à 75% garantit un rendement stable pour la plupart des investissements.
  2. La capture des excédentsLe stop-loss de suivi de 25% permet de réaliser des gains plus importants si la tendance se poursuit.
  3. Dispersion du risqueLes différents mécanismes de retrait réduisent le risque d’une stratégie unique

Système de contrôle des risques: un mécanisme de protection à plusieurs niveaux

1. Contrôle des risques d’entrée

  • Chaque transaction est limitée à 3% du capital du compte.
  • Calcul de position dynamique basée sur l’ATR

2. Gestion du risque de détention

  • Stop majeur: 4,5 fois le taux d’ATR
  • Suivi des pertes: ajustement dynamique, blocage des fléaux
  • Prise de contrôle supplémentaire: 10% de protection des gains fixes

3. Filtrage du signal Les quatre indicateurs techniques ont été confirmés et ont considérablement réduit la probabilité de faux signaux.

Analyse des atouts et des limites de la stratégie

Avantages:

  1. Qualité du signalLe système de filtrage multiple a considérablement amélioré la fiabilité des signaux de transaction.
  2. Les risques sont maîtrisés: Système de gestion de stop-loss et de position parfait
  3. Très adaptableATR: dynamique d’ajustement pour s’adapter à différentes conditions de marché
  4. Optimisation des résultatsLa stratégie de répartition des positions a équilibré les gains stables et les gains excédentaires.

Limites potentielles:

  1. La dépendance à la tendanceLe marché de l’immobilier est en plein essor et les investisseurs devraient s’attendre à une baisse.
  2. Paramètres sensibles: Plusieurs paramètres doivent être optimisés pour les différentes variétés
  3. Le retardLe site de l’UNICEF a publié une vidéo montrant les retards d’entrée en raison de nombreux filtres.

Recommandations pour une utilisation au combat

1. Sélection des variétés Choisissez des variétés à forte tendance, telles que les principales paires de devises, les futures sur indices boursiers, etc.

2. Optimisation des paramètres Il est recommandé d’optimiser le retracement en fonction des données historiques de chaque variété de transaction, en se concentrant particulièrement sur:

  • Cycle d’échantillonnage du canal de Gauss
  • La longueur du cycle de Kijun-Sen
  • Le multiplicateur de stop loss ATR

3. Adaptation au marché En cas de choc évident du marché, il peut être envisagé de suspendre la stratégie ou d’ajuster les paramètres.

Résumé: Une approche systémique pour quantifier les transactions

La valeur de cette stratégie ne réside pas seulement dans sa mise en œuvre technique, mais aussi dans la pensée systémique qu’elle incarne:

  1. Vérification multidimensionnelleLes signaux de transaction sont vérifiés à partir de tendances, volumes et volatilité.
  2. La priorité au risqueUne bonne gestion des risques est la base de la stratégie
  3. Optimisation des résultatsL’objectif est d’équilibrer les différents objectifs de revenus par une stratégie de répartition des positions.

Pour les traders quantifiés, cette stratégie fournit un excellent cadre de référence. La clé n’est pas de suivre les paramètres, mais de comprendre son idée de conception et de l’ajuster en fonction de sa propre variété de trading et de ses préférences en matière de risque.

N’oubliez pas que la meilleure stratégie n’est pas la plus complexe, mais celle qui convient le mieux à votre style de trading et à votre environnement de marché.

Code source de la stratégie
/*backtest
start: 2025-01-01 00:00:00
end: 2025-04-01 00:00:00
period: 1h
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"ETH_USDT","balance":500000}]
*/

// @version=6
strategy("Gaussian Channel Strategy – GC + Kijun (120) + VAPI Gate + ATR(4.5x) + 75/25 TP-TRAIL + Extra %TP",
     overlay=true)

// =============================
// ======= INPUTS ==============
// =============================
N_poles   = input.int(4,   "Gaussian Poles", minval=1, maxval=9)
per       = input.int(144, "Sampling Period", minval=2)
mult      = input.float(1.414, "Filtered TR Multiplier", step=0.001)
src       = input.source(hlc3, "Source")
modeLag   = input.bool(false, "Reduced Lag Mode")
modeFast  = input.bool(false, "Fast Response Mode")

kijunLen  = input.int(130, "Kijun-Sen Period")

vapiLen   = input.int(10, "VAPI Length")
vapiThresh= input.float(0.0, "VAPI Threshold (0 = zero line)")

atrLen    = input.int(11, "ATR Length (RMA)")
slATRmul  = input.float(4.5, "SL = ATR ×", step=0.1)
rr_fixed  = input.float(3.5, "Fixed TP RR (Leg A)", step=0.1)
allocA    = input.float(75,  "Allocation %: Fixed TP Leg", minval=1, maxval=99)
riskPct   = input.float(3.0, "Risk % of Equity per Trade", step=0.1, minval=0.1, maxval=10)

tpEnable    = input.bool(true,  "Enable Extra % Take Profit")
tpPctLong   = input.float(10.0, "Extra Long TP % of Entry",  step=0.1, minval=0)
tpPctShort  = input.float(10.0, "Extra Short TP % of Entry", step=0.1, minval=0)

// =============================
// ===== CORE COMPONENTS =======
// =============================
atr = ta.rma(ta.tr(true), atrLen)

donchian_avg(len) => (ta.highest(high, len) + ta.lowest(low, len)) / 2.0
kijun = donchian_avg(kijunLen)

// --- VAPI_LB (LazyBear) ---
rs(x, len) => ta.cum(x) - nz(ta.cum(x)[len])
v_x   = (2*close - high - low) / math.max(high - low, syminfo.mintick)
v_tva = rs(volume * v_x, vapiLen)
v_tv  = rs(volume, vapiLen)
v_va  = 100 * (v_tva / v_tv)

// =============================
// ===== Gaussian Channel ======
// =============================
f_filt9x(_a, _s, _i) =>
    int _m2 = 0, int _m3 = 0, int _m4 = 0, int _m5 = 0, int _m6 = 0,
    int _m7 = 0, int _m8 = 0, int _m9 = 0, float _f = 0.0, _x = (1 - _a)
    _m2 := _i == 9 ? 36  : _i == 8 ? 28 : _i == 7 ? 21 : _i == 6 ? 15 : _i == 5 ? 10 : _i == 4 ? 6 : _i == 3 ? 3 : _i == 2 ? 1 : 0
    _m3 := _i == 9 ? 84  : _i == 8 ? 56 : _i == 7 ? 35 : _i == 6 ? 20 : _i == 5 ? 10 : _i == 4 ? 4 : _i == 3 ? 1 : 0
    _m4 := _i == 9 ? 126 : _i == 8 ? 70 : _i == 7 ? 35 : _i == 6 ? 15 : _i == 5 ? 5  : _i == 4 ? 1 : 0
    _m5 := _i == 9 ? 126 : _i == 8 ? 56 : _i == 7 ? 21 : _i == 6 ? 6  : _i == 5 ? 1  : 0 
    _m6 := _i == 9 ? 84  : _i == 8 ? 28 : _i == 7 ? 7  : _i == 6 ? 1  : 0 
    _m7 := _i == 9 ? 36  : _i == 8 ? 8  : _i == 7 ? 1  : 0 
    _m8 := _i == 9 ? 9   : _i == 8 ? 1  : 0 
    _m9 := _i == 9 ? 1   : 0
    _f := math.pow(_a, _i) * nz(_s) +
         _i  *     _x      * nz(_f[1])      - (_i >= 2 ?
         _m2 * math.pow(_x, 2)  * nz(_f[2]) : 0) + (_i >= 3 ?
         _m3 * math.pow(_x, 3)  * nz(_f[3]) : 0) - (_i >= 4 ?
         _m4 * math.pow(_x, 4)  * nz(_f[4]) : 0) + (_i >= 5 ?
         _m5 * math.pow(_x, 5)  * nz(_f[5]) : 0) - (_i >= 6 ?
         _m6 * math.pow(_x, 6)  * nz(_f[6]) : 0) + (_i >= 7 ?
         _m7 * math.pow(_x, 7)  * nz(_f[7]) : 0) - (_i >= 8 ?
         _m8 * math.pow(_x, 8)  * nz(_f[8]) : 0) + (_i == 9 ?
         _m9 * math.pow(_x, 9)  * nz(_f[9]) : 0)

f_pole(_a, _s, _i) =>
    _f1 =            f_filt9x(_a, _s, 1),      _f2 = (_i >= 2 ? f_filt9x(_a, _s, 2) : 0), _f3 = (_i >= 3 ? f_filt9x(_a, _s, 3) : 0)
    _f4 = (_i >= 4 ? f_filt9x(_a, _s, 4) : 0), _f5 = (_i >= 5 ? f_filt9x(_a, _s, 5) : 0), _f6 = (_i >= 6 ? f_filt9x(_a, _s, 6) : 0)
    _f7 = (_i >= 7 ? f_filt9x(_a, _s, 7) : 0), _f8 = (_i >= 8 ? f_filt9x(_a, _s, 8) : 0), _f9 = (_i == 9 ? f_filt9x(_a, _s, 9) : 0)
    _fn = _i == 1 ? _f1 : _i == 2 ? _f2 : _i == 3 ? _f3 : _i == 4 ? _f4 : _i == 5 ? _f5 : _i == 6 ? _f6 : _i == 7 ? _f7 : _i == 8 ? _f8 : _i == 9 ? _f9 : na
    [_fn, _f1]

beta  = (1 - math.cos(4*math.asin(1)/per)) / (math.pow(1.414, 2/N_poles) - 1)
alpha = - beta + math.sqrt(math.pow(beta, 2) + 2*beta)

lag = (per - 1) / (2.0 * N_poles)

srcdata = modeLag ? src + (src - nz(src[lag])) : src
tr_raw  = ta.tr(true)
trdata  = modeLag ? tr_raw + (tr_raw - nz(tr_raw[lag])) : tr_raw

[filt_n, filt_1]       = f_pole(alpha, srcdata, N_poles)
[filt_n_tr, filt_1_tr] = f_pole(alpha, trdata,  N_poles)

filt   = modeFast ? (filt_n + filt_1)/2.0 : filt_n
filttr = modeFast ? (filt_n_tr + filt_1_tr)/2.0 : filt_n_tr

hband = filt + filttr * mult
lband = filt - filttr * mult

// =============================
// ===== Signals & Filters =====
// =============================
doLong  = close > filt and close > kijun and v_va > vapiThresh
doShort = close < filt and close < kijun and v_va < -vapiThresh

// =============================
// ===== Position Sizing =======
// =============================
riskValue   = strategy.equity * (riskPct/100.0)
slDist      = atr * slATRmul
qtyTotal    = slDist > 0 ? riskValue / slDist : 0.0
qtyA        = qtyTotal * (allocA/100.0)
qtyB        = qtyTotal * ((100 - allocA)/100.0)

// =============================
// ===== Order Execution =======
// =============================
var float trailStopL = na
var float trailStopS = na

inLong  = strategy.position_size > 0
inShort = strategy.position_size < 0
entryPx = strategy.position_avg_price

// Entries
if doLong and not inLong and strategy.position_size <= 0
    strategy.order("L-A", strategy.long, qty=qtyA)
    strategy.order("L-B", strategy.long, qty=qtyB)
    trailStopL := na
if doShort and not inShort and strategy.position_size >= 0
    strategy.order("S-A", strategy.short, qty=qtyA)
    strategy.order("S-B", strategy.short, qty=qtyB)
    trailStopS := na

// LONG management
if inLong
    slL = entryPx - slDist
    tpA = entryPx + rr_fixed * slDist

    // Leg A: 固定RR止盈 + 止损
    strategy.exit("TP/SL-LA", from_entry="L-A", limit=tpA, stop=slL)

    // Leg B: 追踪止损
    trailStopL := na(trailStopL[1]) or strategy.position_size[1] <= 0 ? slL : math.max(trailStopL[1], close - slDist)
    strategy.exit("Trail-LB", from_entry="L-B", stop=trailStopL)

    // 额外百分比止盈
    if tpEnable and high >= entryPx * (1 + tpPctLong/100.0)
        strategy.close("L-A", comment="ExtraTP")
        strategy.close("L-B", comment="ExtraTP")

// SHORT management
if inShort
    slS = entryPx + slDist
    tpA = entryPx - rr_fixed * slDist

    // Leg A: 固定RR止盈 + 止损
    strategy.exit("TP/SL-SA", from_entry="S-A", limit=tpA, stop=slS)

    // Leg B: 追踪止损
    trailStopS := na(trailStopS[1]) or strategy.position_size[1] >= 0 ? slS : math.min(trailStopS[1], close + slDist)
    strategy.exit("Trail-SB", from_entry="S-B", stop=trailStopS)

    // 额外百分比止盈
    if tpEnable and low <= entryPx * (1 - tpPctShort/100.0)
        strategy.close("S-A", comment="ExtraTP")
        strategy.close("S-B", comment="ExtraTP")

// =============================
// ===== 图表绘制 ==============
// =============================
fcolor = filt > nz(filt[1]) ? color.new(color.lime, 0) : filt < nz(filt[1]) ? color.new(color.red, 0) : color.new(color.gray, 0)
plotFilter = plot(filt,  title="GC Filter",    color=fcolor, linewidth=2)
plotH      = plot(hband, title="GC High Band", color=fcolor)
plotL      = plot(lband, title="GC Low Band",  color=fcolor)
fill(plotH, plotL, color=color.new(fcolor, 80))

plot(kijun, "Kijun-Sen", color=color.new(color.maroon, 0))

// 信号标记
plotshape(doLong,  title="Long Setup",  style=shape.triangleup,   location=location.belowbar, color=color.new(color.lime, 0), size=size.tiny, text="ENTRY L")
plotshape(doShort, title="Short Setup", style=shape.triangledown, location=location.abovebar, color=color.new(color.fuchsia, 0), size=size.tiny, text="ENTRY S")