From 987188e41f15e5914686c2637f4ddee418af9be8 Mon Sep 17 00:00:00 2001 From: Matthias Date: Fri, 3 Jul 2020 19:58:02 +0200 Subject: [PATCH] Add avgduration for winners and losers --- docs/backtesting.md | 40 ++++++++++++++------------ freqtrade/optimize/optimize_reports.py | 9 ++++++ 2 files changed, 31 insertions(+), 18 deletions(-) diff --git a/docs/backtesting.md b/docs/backtesting.md index 6c01e1c62..cb20c3e43 100644 --- a/docs/backtesting.md +++ b/docs/backtesting.md @@ -224,23 +224,26 @@ The last element of the backtest report is the summary metrics table. It contains some useful key metrics about your strategy. ``` -============ SUMMARY METRICS ============= -| Metric | Value | -|------------------+---------------------| -| Total trades | 429 | -| First trade | 2019-01-01 18:30:00 | -| First trade Pair | EOS/USDT | -| Backtesting from | 2019-01-01 00:00:00 | -| Backtesting to | 2019-05-01 00:00:00 | -| Trades per day | 3.575 | -| Best day | 25.27% | -| Worst day | -30.67% | -| | | -| Max Drawdown | 50.63% | -| Drawdown Start | 2019-02-15 14:10:00 | -| Drawdown End | 2019-04-11 18:15:00 | -| Market change | -5.88% | -========================================== +=============== SUMMARY METRICS =============== +| Metric | Value | +|-----------------------+---------------------| + +| Total trades | 429 | +| First trade | 2019-01-01 18:30:00 | +| First trade Pair | EOS/USDT | +| Backtesting from | 2019-01-01 00:00:00 | +| Backtesting to | 2019-05-01 00:00:00 | +| Trades per day | 3.575 | +| Best day | 25.27% | +| Worst day | -30.67% | +| Avg. Duration Winners | 4:23:00 | +| Avg. Duration Loser | 6:55:00 | +| | | +| Max Drawdown | 50.63% | +| Drawdown Start | 2019-02-15 14:10:00 | +| Drawdown End | 2019-04-11 18:15:00 | +| Market change | -5.88% | +=============================================== ``` @@ -250,10 +253,11 @@ It contains some useful key metrics about your strategy. - `Backtesting from` / `Backtesting to`: Backtesting range (usually defined as `--timerange from-to`). - `Trades per day`: Total trades / Backtest duration (this will give you information about how many trades to expect from the strategy). - `Best day` / `Worst day`: Best and worst day based on daily profit. +- `Avg. Duration Winners` / `Avg. Duration Loser`: Average durations for winning and losing trades. - `Max Drawdown`: Maximum drawown experienced. a value of 50% means that from highest to subsequent lowest point, a 50% drop was experiened). - `Drawdown Start` / `Drawdown End`: From when to when was this large drawdown (can also be visualized via `plot-dataframe` subcommand). - `Market change`: Change of the market during the backtest period. Calculated as average of all pairs changes from the first to the last candle using the "close" column. - + ### Assumptions made by backtesting Since backtesting lacks some detailed information about what happens within a candle, it needs to take a few assumptions: diff --git a/freqtrade/optimize/optimize_reports.py b/freqtrade/optimize/optimize_reports.py index 33157d50a..f9b38caf0 100644 --- a/freqtrade/optimize/optimize_reports.py +++ b/freqtrade/optimize/optimize_reports.py @@ -218,12 +218,19 @@ def generate_daily_stats(results: DataFrame) -> Dict[str, Any]: draw_days = sum(daily_profit == 0) losing_days = sum(daily_profit < 0) + winning_trades = results.loc[results['profit_percent'] > 0] + losing_trades = results.loc[results['profit_percent'] < 0] + return { 'backtest_best_day': best, 'backtest_worst_day': worst, 'winning_days': winning_days, 'draw_days': draw_days, 'losing_days': losing_days, + 'winner_holding_avg': (timedelta(minutes=round(winning_trades['trade_duration'].mean())) + if not winning_trades.empty else '0:00'), + 'loser_holding_avg': (timedelta(minutes=round(losing_trades['trade_duration'].mean())) + if not losing_trades.empty else '0:00'), } @@ -390,6 +397,8 @@ def text_table_add_metrics(strat_results: Dict) -> str: ('Worst day', f"{round(strat_results['backtest_worst_day'] * 100, 2)}%"), ('Days win/draw/lose', f"{strat_results['winning_days']} / " f"{strat_results['draw_days']} / {strat_results['losing_days']}"), + ('Avg. Duration Winners', f"{strat_results['winner_holding_avg']}"), + ('Avg. Duration Loser', f"{strat_results['loser_holding_avg']}"), ('', ''), # Empty line to improve readability ('Max Drawdown', f"{round(strat_results['max_drawdown'] * 100, 2)}%"), ('Drawdown Start', strat_results['drawdown_start'].strftime(DATETIME_PRINT_FORMAT)),