From: Jérôme Benoit Date: Wed, 26 Feb 2025 10:35:50 +0000 (+0100) Subject: refactor(qav3): fine tune default values X-Git-Url: https://git.piment-noir.org/?a=commitdiff_plain;h=9ddd0f96425eb90f687824560ffc629d71f19823;p=freqai-strategies.git refactor(qav3): fine tune default values Signed-off-by: Jérôme Benoit --- diff --git a/quickadapter/user_data/freqaimodels/LightGBMRegressorQuickAdapterV35.py b/quickadapter/user_data/freqaimodels/LightGBMRegressorQuickAdapterV35.py index f368eae..8a50f79 100644 --- a/quickadapter/user_data/freqaimodels/LightGBMRegressorQuickAdapterV35.py +++ b/quickadapter/user_data/freqaimodels/LightGBMRegressorQuickAdapterV35.py @@ -272,7 +272,7 @@ class LightGBMRegressorQuickAdapterV35(BaseRegressionModel): ) -> tuple[float, float]: predictions_smoothing = self.freqai_info.get("predictions_smoothing", "mean") if predictions_smoothing == "quantile": - return quantile_min_max_pred( + return self.quantile_min_max_pred( pred_df, fit_live_predictions_candles, label_period_candles ) elif predictions_smoothing == "mean": @@ -490,6 +490,29 @@ class LightGBMRegressorQuickAdapterV35(BaseRegressionModel): except ValueError: return False + def quantile_min_max_pred( + self, + pred_df: pd.DataFrame, + fit_live_predictions_candles: int, + label_period_candles: int, + ) -> tuple[float, float]: + pred_df_sorted = ( + pred_df.select_dtypes(exclude=["object"]) + .copy() + .apply(lambda col: col.sort_values(ascending=False, ignore_index=True)) + ) + + label_period_frequency: int = int( + fit_live_predictions_candles / (label_period_candles * 2) + ) + min_pred = pred_df_sorted.iloc[-label_period_frequency:].quantile( + self.freqai_info.get("min_quantile", 0.25) + ) + max_pred = pred_df_sorted.iloc[:label_period_frequency].quantile( + self.freqai_info.get("max_quantile", 0.75) + ) + return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] + def mean_min_max_pred( pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int @@ -508,23 +531,6 @@ def mean_min_max_pred( return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] -def quantile_min_max_pred( - pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int -) -> tuple[float, float]: - pred_df_sorted = ( - pred_df.select_dtypes(exclude=["object"]) - .copy() - .apply(lambda col: col.sort_values(ascending=False, ignore_index=True)) - ) - - label_period_frequency: int = int( - fit_live_predictions_candles / (label_period_candles * 2) - ) - min_pred = pred_df_sorted.iloc[-label_period_frequency:].quantile(0.25) - max_pred = pred_df_sorted.iloc[:label_period_frequency].quantile(0.75) - return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] - - def median_min_max_pred( pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int ) -> tuple[float, float]: @@ -555,7 +561,7 @@ def period_objective( candles_step, model_training_parameters, ) -> float: - min_train_window: int = 600 + min_train_window: int = fit_live_predictions_candles * 2 max_train_window: int = ( len(X) if len(X) > min_train_window else (min_train_window + len(X)) ) diff --git a/quickadapter/user_data/freqaimodels/XGBoostRegressorQuickAdapterV35.py b/quickadapter/user_data/freqaimodels/XGBoostRegressorQuickAdapterV35.py index 0326a78..a1438bd 100644 --- a/quickadapter/user_data/freqaimodels/XGBoostRegressorQuickAdapterV35.py +++ b/quickadapter/user_data/freqaimodels/XGBoostRegressorQuickAdapterV35.py @@ -273,7 +273,7 @@ class XGBoostRegressorQuickAdapterV35(BaseRegressionModel): ) -> tuple[float, float]: predictions_smoothing = self.freqai_info.get("predictions_smoothing", "mean") if predictions_smoothing == "quantile": - return quantile_min_max_pred( + return self.quantile_min_max_pred( pred_df, fit_live_predictions_candles, label_period_candles ) elif predictions_smoothing == "mean": @@ -491,6 +491,29 @@ class XGBoostRegressorQuickAdapterV35(BaseRegressionModel): except ValueError: return False + def quantile_min_max_pred( + self, + pred_df: pd.DataFrame, + fit_live_predictions_candles: int, + label_period_candles: int, + ) -> tuple[float, float]: + pred_df_sorted = ( + pred_df.select_dtypes(exclude=["object"]) + .copy() + .apply(lambda col: col.sort_values(ascending=False, ignore_index=True)) + ) + + label_period_frequency: int = int( + fit_live_predictions_candles / (label_period_candles * 2) + ) + min_pred = pred_df_sorted.iloc[-label_period_frequency:].quantile( + self.freqai_info.get("min_quantile", 0.25) + ) + max_pred = pred_df_sorted.iloc[:label_period_frequency].quantile( + self.freqai_info.get("max_quantile", 0.75) + ) + return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] + def mean_min_max_pred( pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int @@ -509,23 +532,6 @@ def mean_min_max_pred( return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] -def quantile_min_max_pred( - pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int -) -> tuple[float, float]: - pred_df_sorted = ( - pred_df.select_dtypes(exclude=["object"]) - .copy() - .apply(lambda col: col.sort_values(ascending=False, ignore_index=True)) - ) - - label_period_frequency: int = int( - fit_live_predictions_candles / (label_period_candles * 2) - ) - min_pred = pred_df_sorted.iloc[-label_period_frequency:].quantile(0.25) - max_pred = pred_df_sorted.iloc[:label_period_frequency].quantile(0.75) - return min_pred[EXTREMA_COLUMN], max_pred[EXTREMA_COLUMN] - - def median_min_max_pred( pred_df: pd.DataFrame, fit_live_predictions_candles: int, label_period_candles: int ) -> tuple[float, float]: @@ -556,7 +562,7 @@ def period_objective( candles_step, model_training_parameters, ) -> float: - min_train_window: int = 600 + min_train_window: int = fit_live_predictions_candles * 2 max_train_window: int = ( len(X) if len(X) > min_train_window else (min_train_window + len(X)) ) diff --git a/quickadapter/user_data/strategies/QuickAdapterV3.py b/quickadapter/user_data/strategies/QuickAdapterV3.py index bbf89ec..0160834 100644 --- a/quickadapter/user_data/strategies/QuickAdapterV3.py +++ b/quickadapter/user_data/strategies/QuickAdapterV3.py @@ -103,9 +103,9 @@ class QuickAdapterV3(IStrategy): }, { "method": "StoplossGuard", - "lookback_period_candles": fit_live_predictions_candles, + "lookback_period_candles": int(fit_live_predictions_candles / 2), "trade_limit": 1, - "stop_duration_candles": fit_live_predictions_candles, + "stop_duration_candles": int(fit_live_predictions_candles / 2), "only_per_pair": True, }, ]