
Chiến lược này là một hệ thống giao dịch tương lai cao cấp, kết hợp nhiều điều kiện kỹ thuật và phân tích khung thời gian cao hơn để xác định cơ hội giao dịch có khả năng cao. Chiến lược này sử dụng phương pháp dựa trên kết hợp nhiều điều kiện, yêu cầu nhiều điều kiện kỹ thuật được đáp ứng cùng một lúc để tham gia giao dịch. Nó tích hợp một số khái niệm kỹ thuật tiên tiến, bao gồm lỗ hổng giá trị công bằng (FVG), khối lệnh (Order Blocks), quét thanh khoản (Liquidity Sweeps) và tín hiệu phá vỡ cấu trúc (BOS), đồng thời sử dụng các chỉ số xác nhận xu hướng trong các chu kỳ thời gian khác nhau.
Cốt lõi của chiến lược này là sử dụng sự kết hợp của nhiều phương pháp phân tích kỹ thuật để đảm bảo chỉ tham gia giao dịch khi có nhiều chỉ số báo hiệu cùng một lúc. Cụ thể, chiến lược bao gồm một số thành phần quan trọng sau:
Chiến lược chỉ tạo ra một tín hiệu vào khi có ít nhất hai điều kiện cơ bản (một trong chế độ khởi động) cộng với tín hiệu phá vỡ cấu trúc và đồng thời phù hợp với xu hướng thời gian cao hơn.
Về quản lý rủi ro, chiến lược này sử dụng ATR để thiết lập vị trí dừng động, với khoảng cách dừng thường là 1,5 lần so với ATR. Phương pháp này làm tăng khoảng cách dừng khi có biến động cao và giảm khoảng cách khi có biến động thấp, làm cho dừng lại thông minh hơn.
Đối với kết thúc lợi nhuận, chiến lược sử dụng phương pháp lợi nhuận theo đợt, thu lợi nhuận 50% khi đạt được lợi nhuận tương đương với rủi ro ((1R)), đồng thời di chuyển khoản lỗ hổng còn lại sang vị trí bảo hiểm, tạo cơ hội giao dịch không rủi ro. Ngoài ra, có cơ chế thoát dựa trên thời gian, nếu giao dịch không di chuyển theo hướng có lợi trong thời gian được chỉ định ((30 phút mặc định), nó sẽ tự động đóng.
Ngoài ra, chiến lược này cũng bao gồm chức năng quản lý tài khoản, tự động rút khỏi tất cả các vị trí khi tài khoản đạt được mục tiêu đặt trước (khoảng \( 3000) hoặc kích hoạt dừng theo dõi (khoảng \) 2500 sau khi bắt đầu theo dõi).
Sau khi phân tích sâu về mã, chúng tôi có thể tóm tắt một số ưu điểm rõ ràng:
Mặc dù chiến lược này được thiết kế tốt, nhưng vẫn có một số rủi ro tiềm ẩn, bao gồm:
Dựa trên phân tích của mã, đây là một số hướng tối ưu hóa tiềm năng:
Đây là một chiến lược giao dịch tương lai đa chỉ số được thiết kế tốt, kết hợp nhiều khái niệm phân tích kỹ thuật tiên tiến, và có chức năng quản lý rủi ro và quản lý vốn hoàn hảo. Nó làm giảm tín hiệu giả mạo bằng cách yêu cầu nhiều điều kiện được đáp ứng cùng một lúc và xác nhận xu hướng thời gian cao, đồng thời sử dụng chiến lược dừng lỗ động và thu lợi nhuận theo đợt dựa trên ATR để tối ưu hóa tỷ lệ lợi nhuận rủi ro.
Ưu điểm chính của chiến lược này là hệ thống xác nhận nhiều lớp và quản lý rủi ro thông minh, cho phép nó nắm bắt các cơ hội giao dịch có xác suất cao trong khi vẫn giữ rủi ro thấp. Tuy nhiên, sự phức tạp của chiến lược cũng đưa ra những thách thức về tối ưu hóa tham số và khả năng thích ứng của thị trường, cần phải duy trì hiệu quả của nó thông qua giám sát liên tục và điều chỉnh thường xuyên.
Bằng cách thực hiện các biện pháp tối ưu hóa được đề xuất, đặc biệt là tăng cường khả năng thích ứng với tình trạng thị trường và cải thiện hệ thống quản lý rủi ro, chiến lược này có tiềm năng duy trì hiệu suất ổn định trong các môi trường thị trường khác nhau. Nói chung, đây là một chiến lược tiên tiến phù hợp cho các nhà giao dịch có kinh nghiệm sử dụng và có thể trở thành một công cụ mạnh mẽ trong hệ thống giao dịch, với sự giám sát và điều chỉnh thích hợp.
/*backtest
start: 2024-04-02 00:00:00
end: 2025-04-01 00:00:00
period: 2d
basePeriod: 2d
exchanges: [{"eid":"Futures_Binance","currency":"ETH_USDT"}]
*/
// @version=5
strategy("NQ Futures Trading Strategy", overlay=true, initial_capital=50000, default_qty_type=strategy.cash, default_qty_value=5000)
// ==========================================
// Parameters
// ==========================================
// Account Parameters
accountSize = 50000
profitGoal = 3000
trailingThreshold = 2500
stopsTrailing = 52650
// Trading Parameters
atrLength = input.int(14, "ATR Period", minval=1)
atrMultiplier = input.float(1.5, "ATR Multiplier for SL", minval=0.5, maxval=3.0, step=0.1)
timeoutPeriod = input.int(30, "Exit after X minutes if trade doesn't move favorably", minval=5, maxval=120)
// FVG (Fair Value Gap) Parameters
fvgLength = input.int(5, "FVG Look-back Period", minval=2, maxval=20)
fvgThreshold = input.float(0.1, "FVG Size Threshold (%)", minval=0.05, maxval=1.0, step=0.05) * 0.01
// Order Block Parameters
obLength = input.int(5, "Order Block Look-back Period", minval=2, maxval=20)
obThreshold = input.float(0.1, "Order Block Size Threshold (%)", minval=0.05, maxval=1.0, step=0.05) * 0.01
// Liquidity Sweep Parameters
sweepLength = input.int(5, "Liquidity Sweep Look-back Period", minval=2, maxval=20)
sweepThreshold = input.float(0.05, "Sweep Size Threshold (%)", minval=0.01, maxval=0.5, step=0.01) * 0.01
// Break of Structure Parameters
bosLength = input.int(5, "BOS Look-back Period", minval=2, maxval=20)
bosThreshold = input.float(0.05, "BOS Size Threshold (%)", minval=0.01, maxval=0.5, step=0.01) * 0.01
// Debug Mode
debugMode = input.bool(false, "Debug Mode (more signals)")
// Higher Timeframe Trend Parameters
htfPeriod1 = input.timeframe("15", "First Higher Timeframe")
htfPeriod2 = input.timeframe("60", "Second Higher Timeframe")
// ==========================================
// Indicators & Calculations
// ==========================================
// ATR Calculation
atr = ta.atr(atrLength)
// Higher Timeframe EMAs for Trend Determination
htf1_ema20 = request.security(syminfo.tickerid, htfPeriod1, ta.ema(close, 20), barmerge.gaps_off, barmerge.lookahead_off)
htf1_ema50 = request.security(syminfo.tickerid, htfPeriod1, ta.ema(close, 50), barmerge.gaps_off, barmerge.lookahead_off)
htf2_ema20 = request.security(syminfo.tickerid, htfPeriod2, ta.ema(close, 20), barmerge.gaps_off, barmerge.lookahead_off)
htf2_ema50 = request.security(syminfo.tickerid, htfPeriod2, ta.ema(close, 50), barmerge.gaps_off, barmerge.lookahead_off)
// Higher Timeframe Trend
htf1_bullish = htf1_ema20 > htf1_ema50
htf1_bearish = htf1_ema20 < htf1_ema50
htf2_bullish = htf2_ema20 > htf2_ema50
htf2_bearish = htf2_ema20 < htf2_ema50
// ==========================================
// Entry Conditions
// ==========================================
// 1. Fair Value Gap (FVG)
bullishFVG = false
bearishFVG = false
for i = 1 to fvgLength
if low[i] > high[i+2] and (low[i] - high[i+2]) / high[i+2] > fvgThreshold
bullishFVG := true
if high[i] < low[i+2] and (low[i+2] - high[i]) / high[i] > fvgThreshold
bearishFVG := true
// 2. Inverse Fair Value Gap
inverseBullishFVG = false
inverseBearishFVG = false
for i = 1 to fvgLength
if high[i+1] < low[i+2] and close[i] > open[i] and close[i] > high[i+1]
inverseBullishFVG := true
if low[i+1] > high[i+2] and close[i] < open[i] and close[i] < low[i+1]
inverseBearishFVG := true
// 3. Order Block / Breaker Block
bullishOrderBlock = false
bearishOrderBlock = false
for i = 1 to obLength
if close[i+1] < open[i+1] and (open[i+1] - close[i+1]) / close[i+1] > obThreshold and close[i] > open[i]
bullishOrderBlock := true
if close[i+1] > open[i+1] and (close[i+1] - open[i+1]) / open[i+1] > obThreshold and close[i] < open[i]
bearishOrderBlock := true
// 4. Liquidity Sweep
bullishSweep = false
bearishSweep = false
lowestLow = ta.lowest(low, sweepLength+1)
highestHigh = ta.highest(high, sweepLength+1)
if low[1] < lowestLow[2] and close > open
bullishSweep := true
if high[1] > highestHigh[2] and close < open
bearishSweep := true
// 5. Break of Structure (BOS)
bullishBOS = false
bearishBOS = false
prevHigh = high[2]
prevLow = low[2]
if high > prevHigh and low[1] < low[2]
bullishBOS := true
if low < prevLow and high[1] > high[2]
bearishBOS := true
// Simpler version for debug mode
if debugMode
bullishBOS := close > open and close > close[1]
bearishBOS := close < open and close < close[1]
// ==========================================
// Signal Generation
// ==========================================
// Count valid entry conditions
bullishConditions = bullishFVG ? 1 : 0
bullishConditions := bullishConditions + (inverseBullishFVG ? 1 : 0)
bullishConditions := bullishConditions + (bullishOrderBlock ? 1 : 0)
bullishConditions := bullishConditions + (bullishSweep ? 1 : 0)
bearishConditions = bearishFVG ? 1 : 0
bearishConditions := bearishConditions + (inverseBearishFVG ? 1 : 0)
bearishConditions := bearishConditions + (bearishOrderBlock ? 1 : 0)
bearishConditions := bearishConditions + (bearishSweep ? 1 : 0)
// Entry signals (need at least 2 conditions + BOS confirmation)
// In debug mode, require only 1 condition
minConditions = debugMode ? 1 : 2
longSignal = bullishConditions >= minConditions and bullishBOS and (htf1_bullish or htf2_bullish)
shortSignal = bearishConditions >= minConditions and bearishBOS and (htf1_bearish or htf2_bearish)
// Debug mode override for testing
if debugMode
longSignal := longSignal or (bullishBOS and htf1_bullish)
shortSignal := shortSignal or (bearishBOS and htf1_bearish)
// ==========================================
// Risk Management
// ==========================================
// Calculate dynamic stop loss based on ATR
longStopDistance = atr * atrMultiplier
shortStopDistance = atr * atrMultiplier
// Default fixed values for testing
if debugMode
longStopDistance := close * 0.01 // 1% stop
shortStopDistance := close * 0.01 // 1% stop
// Calculate position size based on risk
nqPointValue = 20 // Each point is $20 for NQ
longPositionSize = math.floor(2000 / (longStopDistance * nqPointValue))
shortPositionSize = math.floor(2000 / (shortStopDistance * nqPointValue))
// Ensure at least 1 contract
longPositionSize := math.max(longPositionSize, 1)
shortPositionSize := math.max(shortPositionSize, 1)
// Variables to track entry time
var int entryTime = 0
var float equityCurve = accountSize
// ==========================================
// Strategy Execution
// ==========================================
// Make sure we don't get multiple signals on the same bar
var longEnteredThisBar = false
var shortEnteredThisBar = false
longEnteredThisBar := false
shortEnteredThisBar := false
// Entry conditions
if longSignal and not longEnteredThisBar and strategy.position_size <= 0
strategy.close_all()
strategy.entry("Long", strategy.long, qty=longPositionSize)
longEnteredThisBar := true
entryTime := time
if shortSignal and not shortEnteredThisBar and strategy.position_size >= 0
strategy.close_all()
strategy.entry("Short", strategy.short, qty=shortPositionSize)
shortEnteredThisBar := true
entryTime := time
// Take profit and stop loss orders
if strategy.position_size > 0
stopPrice = strategy.position_avg_price - longStopDistance
takeProfitPrice1 = strategy.position_avg_price + longStopDistance
strategy.exit("Long TP1", "Long", qty_percent=50, limit=takeProfitPrice1, stop=stopPrice)
// Move stop to breakeven after 1R move
if high >= takeProfitPrice1
strategy.exit("Long BE", "Long", stop=strategy.position_avg_price)
if strategy.position_size < 0
stopPrice = strategy.position_avg_price + shortStopDistance
takeProfitPrice1 = strategy.position_avg_price - shortStopDistance
strategy.exit("Short TP1", "Short", qty_percent=50, limit=takeProfitPrice1, stop=stopPrice)
// Move stop to breakeven after 1R move
if low <= takeProfitPrice1
strategy.exit("Short BE", "Short", stop=strategy.position_avg_price)
// Time-based exit
if strategy.position_size != 0
currentTime = time
if (currentTime - entryTime) >= timeoutPeriod * 60000 // Convert minutes to milliseconds
strategy.close_all(comment="Time Exit")
// ==========================================
// Trailing Stop for Account Management
// ==========================================
// Update equity curve
equityCurve := strategy.equity
// Check if profit target is reached or trailing stop is hit
if strategy.equity >= accountSize + profitGoal
strategy.close_all(comment="Profit Goal")
if strategy.equity >= accountSize + trailingThreshold
trailingStop = math.max(accountSize, strategy.equity - trailingThreshold)
if strategy.equity <= trailingStop
strategy.close_all(comment="Trailing Stop")
// Stop trailing if account reaches the stop trailing threshold
if strategy.equity >= stopsTrailing
strategy.close_all(comment="Stop Trailing")
// ==========================================
// Plotting
// ==========================================
// Plot entry conditions
plotshape(longSignal, title="Long Signal", location=location.belowbar, color=color.green, style=shape.triangleup, size=size.small)
plotshape(shortSignal, title="Short Signal", location=location.abovebar, color=color.red, style=shape.triangledown, size=size.small)
// Plot current position
bgcolor(strategy.position_size > 0 ? color.new(color.green, 90) : strategy.position_size < 0 ? color.new(color.red, 90) : na)
// Alert conditions
alertcondition(longSignal, title="Long Entry Signal", message="NQ LONG ENTRY: {{ticker}}, Price: {{close}}")
alertcondition(shortSignal, title="Short Entry Signal", message="NQ SHORT ENTRY: {{ticker}}, Price: {{close}}")
alertcondition(strategy.position_size > 0 and high >= strategy.position_avg_price + longStopDistance, title="Long Take Profit", message="NQ LONG TP: {{ticker}}, Price: {{close}}")
alertcondition(strategy.position_size < 0 and low <= strategy.position_avg_price - shortStopDistance, title="Short Take Profit", message="NQ SHORT TP: {{ticker}}, Price: {{close}}")
alertcondition(strategy.position_size > 0 and low <= strategy.position_avg_price - longStopDistance, title="Long Stop Loss", message="NQ LONG SL: {{ticker}}, Price: {{close}}")
alertcondition(strategy.position_size < 0 and high >= strategy.position_avg_price + shortStopDistance, title="Short Stop Loss", message="NQ SHORT SL: {{ticker}}, Price: {{close}}")