退出条件允许趋势交易
This commit is contained in:
parent
6aeb28f32b
commit
971fc5bbde
@ -22,9 +22,23 @@ class FreqaiPrimer(IStrategy):
|
||||
|
||||
stoploss = -0.01 # 固定止损 -1%
|
||||
trailing_stop = True
|
||||
trailing_stop_positive = 0.005 # 价格上涨 0.5% 后开始追踪
|
||||
trailing_stop_positive_offset = 0.008 # 追踪止损偏移量 0.8%
|
||||
|
||||
# 用于跟踪市场状态的数据框缓存
|
||||
_dataframe_cache = None
|
||||
|
||||
@property
|
||||
def trailing_stop_positive(self):
|
||||
"""根据市场状态动态调整跟踪止盈参数"""
|
||||
# 获取当前市场状态
|
||||
if self._dataframe_cache is not None and len(self._dataframe_cache) > 0:
|
||||
current_state = self._dataframe_cache['market_state'].iloc[-1]
|
||||
if current_state == 'strong_bull':
|
||||
return 0.01 # 强劲牛市中放宽跟踪止盈
|
||||
elif current_state == 'weak_bull':
|
||||
return 0.007
|
||||
return 0.005 # 默认值
|
||||
|
||||
timeframe = "3m" # 主时间框架为 3 分钟
|
||||
can_short = False # 禁用做空
|
||||
|
||||
@ -203,14 +217,46 @@ class FreqaiPrimer(IStrategy):
|
||||
return dataframe
|
||||
|
||||
def populate_exit_trend(self, dataframe: DataFrame, metadata: dict) -> DataFrame:
|
||||
# 做多退出(优化以减少亏损)
|
||||
dataframe.loc[
|
||||
(
|
||||
(dataframe['close'] >= dataframe['bb_upper_3m']) |
|
||||
(dataframe['rsi_3m'] > self.rsi_overbought) |
|
||||
(dataframe['close'] > dataframe['open'] + dataframe['atr'] * 2) # 获利2倍ATR
|
||||
),
|
||||
'exit_long'] = 1
|
||||
# 缓存数据框以便在trailing_stop_positive属性中使用
|
||||
self._dataframe_cache = dataframe
|
||||
|
||||
# 基础退出条件
|
||||
basic_exit = (
|
||||
(dataframe['close'] >= dataframe['bb_upper_3m']) |
|
||||
(dataframe['rsi_3m'] > self.rsi_overbought)
|
||||
)
|
||||
|
||||
# 强劲趋势条件:1h趋势向上 + 熊牛得分>70
|
||||
strong_trend = (dataframe['trend_1h_ema'] == 1) & (dataframe['market_score'] > 70)
|
||||
|
||||
# 一般趋势条件:熊牛得分50-70
|
||||
normal_trend = (dataframe['market_score'] >= 50) & (dataframe['market_score'] <= 70)
|
||||
|
||||
# 获取15m数据进行趋势确认
|
||||
df_15m = self.dp.get_pair_dataframe(pair=metadata['pair'], timeframe='15m')
|
||||
df_15m = df_15m.rename(columns={'date': 'date_15m'})
|
||||
merged_data = dataframe.merge(df_15m[['date_15m', 'rsi_15m']], how='left', left_on='date', right_on='date_15m')
|
||||
merged_data = merged_data.fillna(method='ffill')
|
||||
|
||||
# 趋势反转信号:15m RSI超买
|
||||
trend_reversal = merged_data['rsi_15m'] > 75
|
||||
|
||||
# 动态调整退出条件
|
||||
# 强劲趋势中:只有获利达到3倍ATR才退出,或出现明确的趋势反转信号
|
||||
dataframe.loc[strong_trend & ((dataframe['close'] > dataframe['open'] + dataframe['atr'] * 3) | (basic_exit & trend_reversal)), 'exit_long'] = 1
|
||||
|
||||
# 一般趋势中:保持原有2倍ATR退出
|
||||
dataframe.loc[normal_trend & ((dataframe['close'] > dataframe['open'] + dataframe['atr'] * 2) | basic_exit), 'exit_long'] = 1
|
||||
|
||||
# 非趋势或弱势:使用基础条件+1.5倍ATR
|
||||
dataframe.loc[~strong_trend & ~normal_trend & (basic_exit | (dataframe['close'] > dataframe['open'] + dataframe['atr'] * 1.5)), 'exit_long'] = 1
|
||||
|
||||
# 记录退出决策日志
|
||||
if len(dataframe[dataframe['exit_long'] == 1]) > 0:
|
||||
last_exit = dataframe[dataframe['exit_long'] == 1].iloc[-1]
|
||||
current_state = dataframe['market_state'].iloc[-1]
|
||||
logger.info(f"[{metadata['pair']}] 触发退出信号,市场状态: {current_state}, 价格: {last_exit['close']:.2f}")
|
||||
|
||||
return dataframe
|
||||
|
||||
def detect_h1_rapid_rise(self, pair: str, dataframe: DataFrame, metadata: dict) -> tuple[bool, float]:
|
||||
@ -278,12 +324,54 @@ class FreqaiPrimer(IStrategy):
|
||||
logger.error(f"[{pair}] 剧烈拉升检测过程中发生错误: {str(e)}")
|
||||
return False, 0.0
|
||||
|
||||
def custom_stoploss(self, pair: str, trade: 'Trade', current_time, current_rate: float,
|
||||
def custom_stoploss(self, pair: str, trade: 'Trade', current_time, current_rate: float,
|
||||
current_profit: float, **kwargs) -> float:
|
||||
# 动态止损基于ATR
|
||||
dataframe, _ = self.dp.get_analyzed_dataframe(pair, self.timeframe)
|
||||
last_candle = dataframe.iloc[-1]
|
||||
atr = last_candle['atr']
|
||||
|
||||
# 渐进式止损策略
|
||||
if current_profit > 0.03: # 利润超过3%时
|
||||
return -1.5 * atr / current_rate # 扩大止损范围,让利润奔跑
|
||||
elif current_profit > 0.015: # 利润超过1.5%时
|
||||
return -1.2 * atr / current_rate # 轻微扩大止损范围
|
||||
|
||||
if atr > 0:
|
||||
return -1.0 * atr / current_rate # 收紧到1倍ATR
|
||||
return -1.0 * atr / current_rate # 基础1倍ATR止损
|
||||
return self.stoploss
|
||||
|
||||
def custom_exit(self, pair: str, trade: 'Trade', current_time, current_rate: float,
|
||||
current_profit: float, **kwargs) -> float:
|
||||
"""渐进式止盈逻辑"""
|
||||
|
||||
# 获取当前市场状态
|
||||
dataframe, _ = self.dp.get_analyzed_dataframe(pair, self.timeframe)
|
||||
current_state = dataframe['market_state'].iloc[-1] if 'market_state' in dataframe.columns else 'unknown'
|
||||
|
||||
# 定义渐进式止盈水平
|
||||
profit_levels = {
|
||||
# 状态: [(止盈触发利润, 止盈比例)]
|
||||
'strong_bull': [(0.02, 0.3), (0.04, 0.5), (0.06, 0.7), (0.08, 0.9)], # 强劲牛市的渐进止盈
|
||||
'weak_bull': [(0.015, 0.3), (0.03, 0.5), (0.05, 0.8)], # 弱牛市的渐进止盈
|
||||
'neutral': [(0.01, 0.4), (0.02, 0.7), (0.03, 0.9)], # 中性市场的渐进止盈
|
||||
'bear': [(0.008, 0.5), (0.015, 0.8), (0.025, 1.0)] # 熊市的渐进止盈(更保守)
|
||||
}
|
||||
|
||||
# 默认使用中性市场的止盈设置
|
||||
levels = profit_levels.get(current_state, profit_levels['neutral'])
|
||||
|
||||
# 确定当前应该止盈的比例
|
||||
exit_ratio = 0.0
|
||||
for profit_target, ratio in levels:
|
||||
if current_profit >= profit_target:
|
||||
exit_ratio = ratio
|
||||
else:
|
||||
break
|
||||
|
||||
# 记录渐进式止盈决策
|
||||
if exit_ratio > 0:
|
||||
logger.info(f"[{pair}] 渐进式止盈: 当前利润 {current_profit:.2%}, 市场状态 {current_state}, 止盈比例 {exit_ratio:.0%}")
|
||||
|
||||
# 返回应退出的比例(0.0表示不退出,1.0表示全部退出)
|
||||
return exit_ratio
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user