Chiến lược giao cắt đường trung bình động góc xu hướng


Ngày tạo: 2024-01-25 14:35:13 sửa đổi lần cuối: 2024-01-25 14:35:13
sao chép: 2 Số nhấp chuột: 1182
1
tập trung vào
1617
Người theo dõi

Chiến lược giao cắt đường trung bình động góc xu hướng

Tổng quan

Chiến lược này được sử dụng để tính toán độ dốc của đường trung bình, định hướng xu hướng, kết hợp với chỉ số tỷ lệ thay đổi giá, để giao dịch hai chiều dài và ngắn. Bản chất của nó là sử dụng độ dốc của đường trung bình để xác định xu hướng giá, và chiến lược theo dõi xu hướng của chỉ số tỷ lệ thay đổi giá để điều chỉnh hành động.

Nguyên tắc chiến lược

Chiến lược này được đánh giá dựa trên các chỉ số sau:

  1. Góc đường trung bình: Xác định hướng xu hướng của giá bằng cách tính góc độ độ của đường trung bình Jurik và đường trung bình di chuyển của chỉ số. Đường độ lớn hơn 0 là xu hướng tăng, nhỏ hơn 0 là xu hướng giảm.

  2. Tỷ lệ thay đổi giá: tính toán tỷ lệ thay đổi giá đóng cửa của 12 đường K gần đây nhất, lọc các tín hiệu vô hiệu thông qua biến động.

Khi góc đường trung bình lên (((lớn hơn 0)) và tỷ lệ biến đổi giá đáp ứng điều kiện, hãy làm nhiều hơn; khi góc đường trung bình xuống (((nhỏ hơn 0)) và tỷ lệ biến đổi giá đáp ứng điều kiện, hãy làm trống.

Cụ thể, chiến lược này đầu tiên tính toán góc độ lệch của đường trung bình Jurik và EMA. Sau đó, tính toán chỉ số tỷ lệ thay đổi của giá để sử dụng trong thời gian lọc. Khi góc độ đường trung bình chỉ ra xu hướng và tỷ lệ thay đổi giá phù hợp, nó sẽ tạo ra tín hiệu giao dịch.

Phân tích lợi thế

Chiến lược này có những ưu điểm sau:

  1. Sử dụng độ lệch đường trung bình để đánh giá xu hướng rất đáng tin cậy, tỷ lệ thắng cao.

  2. Chỉ số tỷ lệ biến đổi giá có thể lọc hiệu quả sự biến động và tránh giao dịch không hiệu quả.

  3. Jurik trung bình phản ứng nhanh chóng với đột phá, EMA cung cấp một phán đoán xu hướng ổn định, hai thứ này bổ sung cho nhau.

  4. Sử dụng phương thức giao dịch hai chiều dài và ngắn, bạn có thể nắm bắt được các xu hướng trong một xu hướng.

Phân tích rủi ro

Chiến lược này cũng có một số rủi ro:

  1. Khi giá dao động mạnh, đường trung bình có nhiều khả năng tạo ra tín hiệu sai. Bạn có thể giảm nguy cơ này bằng các tham số tối ưu hóa.

  2. Tín hiệu đồng tuyến có thể được chuyển đổi thường xuyên khi vào phiên, tạo ra quá nhiều giao dịch không cần thiết. Các điều kiện lọc bổ sung có thể được thêm vào để giảm giao dịch không hiệu lực.

  3. Khi một sự kiện bất ngờ gây ra giá tăng cao, điểm dừng có thể bị phá vỡ và điểm dừng có thể được nới lỏng thích hợp.

Hướng tối ưu hóa

Chiến lược này có thể được tối ưu hóa theo các khía cạnh sau:

  1. Tối ưu hóa các tham số đường trung bình, tìm kiếm sự kết hợp tham số tốt nhất, tăng sự ổn định của chiến lược.

  2. Tăng các điều kiện lọc như biến động, khối lượng giao dịch, và giảm thêm các giao dịch không hiệu lực.

  3. Kết hợp với các chỉ số khác để xác định điểm dừng lỗ, làm cho dừng lỗ trở nên thông minh hơn.

  4. Phát triển các thuật toán tùy chỉnh kích thước giao dịch để tạo ra lợi nhuận ổn định.

Tóm tắt

Chiến lược này nói chung là một chiến lược theo dõi xu hướng rất thực tế. Nó sử dụng độ lệch đường trung bình để xác định xu hướng rất đáng tin cậy, và chỉ số tỷ lệ biến đổi giá có thể lọc hiệu quả các tín hiệu không hiệu quả. Đồng thời, việc sử dụng phương pháp giao dịch hai chiều dài và ngắn có thể mang lại lợi nhuận tốt hơn. Với sự tối ưu hóa liên tục, chiến lược này có thể trở thành một chiến lược định lượng rất ổn định và đáng tin cậy.

Mã nguồn chiến lược
/*backtest
start: 2023-12-01 00:00:00
end: 2023-12-31 23:59:59
period: 1d
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/

//@version=4
// Based on ma angles code by Duyck which also uses Everget Jurik MA calulation and angle calculation by KyJ
strategy("Trend Angle BF", overlay=false)

/////////////// Time Frame ///////////////
testStartYear = input(2017, "Backtest Start Year") 
testStartMonth = input(1, "Backtest Start Month")
testStartDay = input(1, "Backtest Start Day")
testPeriodStart = timestamp(testStartYear,testStartMonth,testStartDay, 0, 0)

testStopYear = input(2019, "Backtest Stop Year")
testStopMonth = input(12, "Backtest Stop Month")
testStopDay = input(31, "Backtest Stop Day")
testPeriodStop = timestamp(testStopYear,testStopMonth,testStopDay, 0, 0)

testPeriod() => true
    
src=input(ohlc4,title="source")

// definition of "Jurik Moving Average", by Everget
jma(_src,_length,_phase,_power) =>
    phaseRatio = _phase < -100 ? 0.5 : _phase > 100 ? 2.5 : _phase / 100 + 1.5
    beta = 0.45 * (_length - 1) / (0.45 * (_length - 1) + 2)
    alpha = pow(beta, _power)
    jma = 0.0
    e0 = 0.0
    e0 := (1 - alpha) * _src + alpha * nz(e0[1])
    e1 = 0.0
    e1 := (_src - e0) * (1 - beta) + beta * nz(e1[1])
    e2 = 0.0
    e2 := (e0 + phaseRatio * e1 - nz(jma[1])) * pow(1 - alpha, 2) + pow(alpha, 2) * nz(e2[1])
    jma := e2 + nz(jma[1])

//// //// Determine Angle by KyJ //// //// 
angle(_src) =>
    rad2degree=180/3.14159265359  //pi 
    ang=rad2degree*atan((_src[0] - _src[1])/atr(14)) 

jma_line=jma(src,10,50,1)
ma=ema(src,input(56))
jma_slope=angle(jma_line)
ma_slope=angle(ma)

///////////// Rate Of Change ///////////// 
source = close
roclength = input(12, minval=1)
pcntChange = input(2, minval=1)
roc = 100 * (source - source[roclength]) / source[roclength]
emaroc = ema(roc, roclength / 2)
isMoving() => emaroc > (pcntChange / 2) or emaroc < (0 - (pcntChange / 2))

/////////////// Strategy ///////////////
long = ma_slope>=0 and isMoving()
short = ma_slope<=0 and isMoving()

last_long = 0.0
last_short = 0.0
last_long := long ? time : nz(last_long[1])
last_short := short ? time : nz(last_short[1])

long_signal = crossover(last_long, last_short)
short_signal = crossover(last_short, last_long)

last_open_long_signal = 0.0
last_open_short_signal = 0.0
last_open_long_signal := long_signal ? open : nz(last_open_long_signal[1])
last_open_short_signal := short_signal ? open : nz(last_open_short_signal[1])

last_long_signal = 0.0
last_short_signal = 0.0
last_long_signal := long_signal ? time : nz(last_long_signal[1])
last_short_signal := short_signal ? time : nz(last_short_signal[1])

in_long_signal = last_long_signal > last_short_signal
in_short_signal = last_short_signal > last_long_signal

last_high = 0.0
last_low = 0.0
last_high := not in_long_signal ? na : in_long_signal and (na(last_high[1]) or high > nz(last_high[1])) ? high : nz(last_high[1])
last_low := not in_short_signal ? na : in_short_signal and (na(last_low[1]) or low < nz(last_low[1])) ? low : nz(last_low[1])
sl_inp = input(2.0, title='Stop Loss %') / 100
tp_inp = input(900.0, title='Take Profit %') / 100 
 
take_level_l = strategy.position_avg_price * (1 + tp_inp)
take_level_s = strategy.position_avg_price * (1 - tp_inp) 

since_longEntry = barssince(last_open_long_signal != last_open_long_signal[1]) 
since_shortEntry = barssince(last_open_short_signal != last_open_short_signal[1]) 

slLong = in_long_signal ? strategy.position_avg_price * (1 - sl_inp) : na
slShort = strategy.position_avg_price * (1 + sl_inp)
long_sl = in_long_signal ? slLong : na
short_sl = in_short_signal ? slShort : na

/////////////// Execution /////////////// 
if testPeriod()
    strategy.entry("Long",  strategy.long, when=long)
    strategy.entry("Short", strategy.short, when=short)
    strategy.exit("Long Ex", "Long", stop=long_sl, limit=take_level_l, when=since_longEntry > 0)
    strategy.exit("Short Ex", "Short", stop=short_sl, limit=take_level_s, when=since_shortEntry > 0)
    
///////////// Plotting /////////////
hline(0, title='Zero line', color=color.purple, linewidth=1)
plot(ma_slope,title="ma slope", linewidth=2,color=ma_slope>=0?color.lime:color.red)
bgcolor(isMoving() ? long ? color.green : short ? color.red : na : color.white, transp=80)
bgcolor(long_signal ? color.lime : short_signal ? color.red : na, transp=30)