|
| 1 | +""" |
| 2 | +Dual Thrust Strategy - |
| 3 | +Strategy Logic: |
| 4 | + - Buy: When price breaks above the upper threshold (based on previous range) |
| 5 | + - Sell: When price breaks below the lower threshold (based on previous range) |
| 6 | +策略逻辑: |
| 7 | + - 买入:当价格突破上轨(基于前一天的区间) |
| 8 | + - 卖出:当价格突破下轨(基于前一天的区间) |
| 9 | +""" |
| 10 | + |
| 11 | +import pandas as pd |
| 12 | +import numpy as np |
| 13 | +from quanteval.core.strategy import Strategy |
| 14 | + |
| 15 | + |
| 16 | +class DualThrustStrategy(Strategy): |
| 17 | + """ |
| 18 | + Dual Thrust Strategy - A breakout strategy based on price range. |
| 19 | +
|
| 20 | + 双重突破策略,基于价格区间的突破策略。 |
| 21 | +
|
| 22 | + Strategy Logic: |
| 23 | + - Buy: When price breaks above the upper threshold (based on previous range) |
| 24 | + - Sell: When price breaks below the lower threshold (based on previous range) |
| 25 | + 策略逻辑: |
| 26 | + - 买入:当价格突破上轨(基于前一天的区间) |
| 27 | + - 卖出:当价格突破下轨(基于前一天的区间) |
| 28 | + Args: |
| 29 | + k1: 上轨系数 (Upper threshold multiplier, default 0.5) |
| 30 | + k2: 下轨系数 (Lower threshold multiplier, default 0.5) |
| 31 | +
|
| 32 | + Example: |
| 33 | + >>> strategy = DualThrustStrategy(k1=0.5, k2=0.5) |
| 34 | + >>> bt = Backtester(strategy, data) |
| 35 | + >>> results = bt.run() |
| 36 | + """ |
| 37 | + |
| 38 | + def __init__(self, k1: float = 0.5, k2: float = 0.5, window: int = 5): |
| 39 | + super().__init__( |
| 40 | + name=f'DualThrust(k1={k1},k2={k2}, N={window})', k1=k1, k2=k2, window=window |
| 41 | + ) |
| 42 | + |
| 43 | + def generate_signals(self, data: pd.DataFrame) -> pd.Series: |
| 44 | + """ |
| 45 | + 生成交易信号 |
| 46 | +
|
| 47 | + Generate trading signals based on Dual Thrust logic. |
| 48 | +
|
| 49 | + Returns: |
| 50 | + Series with values: |
| 51 | + 1: Long position (price > upper threshold) |
| 52 | + -1: Short position (price < lower threshold) |
| 53 | + 0: No position |
| 54 | + """ |
| 55 | + k1 = self.params['k1'] |
| 56 | + k2 = self.params['k2'] |
| 57 | + n = self.params['window'] |
| 58 | + |
| 59 | + # Calculate previous day's range |
| 60 | + hh = data['High'].shift(1).rolling(window=n).max() |
| 61 | + hc = data['Close'].shift(1).rolling(window=n).max() |
| 62 | + ll = data['Low'].shift(1).rolling(window=n).min() |
| 63 | + lc = data['Close'].shift(1).rolling(window=n).min() |
| 64 | + diff = np.maximum(hh - lc, hc - ll) |
| 65 | + |
| 66 | + # Calculate thresholds |
| 67 | + upper_threshold = data['Open'] + k1 * diff |
| 68 | + lower_threshold = data['Open'] - k2 * diff |
| 69 | + |
| 70 | + # Generate signals |
| 71 | + signals = pd.Series(0, index=data.index) |
| 72 | + signals[data['High'] > upper_threshold] = 1 # Buy signal |
| 73 | + signals[data['Low'] < lower_threshold] = 0 # Sell signal |
| 74 | + |
| 75 | + return signals |
0 commit comments