diff --git a/data/leaderboard.json b/data/leaderboard.json index 0dc11ab..6e7632a 100644 --- a/data/leaderboard.json +++ b/data/leaderboard.json @@ -4,301 +4,361 @@ "author_name": "Will", "strategy_name": "Will Fractals 24h", "description": "Optimized 24-hour fractal breakout strategy with protection mechanisms. Constructs 24h bars from 1-hour close prices only and executes signals on the next 1h bar.", - "last_updated": "2025-05-18T03:24:23.098856Z", + "last_updated": "2025-05-18T13:29:27.618620+00:00Z", "development_metrics": { - "sharpe": 2.4776683641258717, - "total_return": 199232748.5700369, - "max_drawdown": 0.42925570352018166, + "sharpe": 2.457084124502338, + "total_return": 173284349.18098122, + "max_drawdown": 0.46729638078052765, "n_trades": 222, "win_rate": 0.9099099099099099 }, "holdout_metrics": { - "sharpe": 3.975519499218606, - "total_return": 0.22504933857596043, + "sharpe": 3.6758005608147006, + "total_return": 0.20776156850815486, "max_drawdown": 0.03976081539161014, "n_trades": 5, "win_rate": 1.0 } }, { - "author_name": "Genesis", - "strategy_name": "Volatility ATR Strategy", - "description": "Dynamic volatility-based strategy using ATR for entries, stops, and position sizing.", - "last_updated": "2025-05-17T11:49:16.163157Z", - "development_metrics": { - "sharpe": 1.888462660734801, - "total_return": 253424314224.25446, - "max_drawdown": 0.8210335293187818, - "n_trades": 6988, - "win_rate": 0.47510017172295366 - }, - "holdout_metrics": { - "sharpe": 1.6737452346894277, - "total_return": 0.22663205289801103, - "max_drawdown": 0.16424604668618845, - "n_trades": 209, - "win_rate": 0.430622009569378 - } - }, - { - "author_name": "AryanBhargav", - "strategy_name": "Donchian Channel Strategy", - "description": "Trades breakouts based on a 20-period Donchian Channel.", - "last_updated": "2025-05-17T10:48:50.558267Z", + "author_name": "Athon", + "strategy_name": "Buy and Hold", + "description": "Buys Bitcoin at the first bar and holds the position for the entire backtest period.", + "last_updated": "2025-05-18T13:27:50.709799+00:00Z", "development_metrics": { - "sharpe": 1.6853335109249008, - "total_return": 298002959.9805029, - "max_drawdown": 0.9739392202670737, - "n_trades": 1096, - "win_rate": 0.3841240875912409 + "sharpe": 1.4978796081915853, + "total_return": 36965.29154985983, + "max_drawdown": 0.9112345532958346, + "n_trades": 1, + "win_rate": 1.0 }, "holdout_metrics": { - "sharpe": 3.4561142192298537, - "total_return": 0.5106176445329746, - "max_drawdown": 0.06595856609634526, - "n_trades": 34, - "win_rate": 0.4117647058823529 + "sharpe": 0.7304733775172676, + "total_return": 0.0966376804578859, + "max_drawdown": 0.3092850660964837, + "n_trades": 1, + "win_rate": 1.0 } }, { - "author_name": "Adi, Mikey, Alex", - "strategy_name": "Z-Score Moon Mean Revert", - "description": "This PR implements the 'Crying Wolf' trading algorithm, a Z-score mean reversion strategy modulated by natural cyclic phenomena. Entry/exit thresholds adjust based on the moon's cycle, becoming more conservative during full moons when market 'madness' peaks. Our backtesting shows the strategy outperforms during super moons but falters during eclipses. Traditional quants may experience uncontrollable eye-rolling, but as Warren Buffett said, When the moon hits your eye like a big pizza pie, that's a trading opportunity. Our strategy beats buy-and-hold by 1000%, while maintaining a definitively higher sharpe ratio. May the moon shine over us all", - "last_updated": "2025-05-17T12:48:24.059589Z", + "author_name": "Mahak", + "strategy_name": "Advanced Buy And Hold Strategy", + "description": "This strategy aims to provide a robust, adaptive approach that can perform well across different market conditions while managing risk effectively.", + "last_updated": "2025-05-18T13:29:16.591872+00:00Z", "development_metrics": { - "sharpe": 1.6440636071120915, - "total_return": 138493571.09371865, - "max_drawdown": 0.7819300872251194, - "n_trades": 8066, - "win_rate": 0.5090503347384081 + "sharpe": 1.4933060731407406, + "total_return": 31828.251724137932, + "max_drawdown": 0.9112345532958346, + "n_trades": 1, + "win_rate": 1.0 }, "holdout_metrics": { - "sharpe": 0.9504328150744347, - "total_return": 0.12252505311449768, - "max_drawdown": 0.1671603743892358, - "n_trades": 229, - "win_rate": 0.4847161572052402 + "sharpe": 0.5471567498458149, + "total_return": 0.057312580028671345, + "max_drawdown": 0.3092850660964837, + "n_trades": 1, + "win_rate": 1.0 } }, { "author_name": "Jim", "strategy_name": "Enhanced Price Momentum", "description": "Enhanced momentum strategy with trend confirmation, volatility-based position sizing, and risk management.", - "last_updated": "2025-05-17T12:50:15.376811Z", + "last_updated": "2025-05-18T13:29:02.193272+00:00Z", "development_metrics": { - "sharpe": 1.5028615712789264, - "total_return": 83691.01305699791, + "sharpe": 1.457055976987805, + "total_return": 18313.95998687873, "max_drawdown": 0.8047181682279175, "n_trades": 175, "win_rate": 0.4685714285714286 }, "holdout_metrics": { - "sharpe": 2.3589800460822663, - "total_return": 0.25319737220833005, - "max_drawdown": 0.09536946074759874, + "sharpe": 1.720988585986783, + "total_return": 0.17628421979081077, + "max_drawdown": 0.1066612192749351, "n_trades": 8, "win_rate": 0.75 } }, { - "author_name": "Mahak", - "strategy_name": "Advanced Buy And Hold Strategy", - "description": "This strategy aims to provide a robust, adaptive approach that can perform well across different market conditions while managing risk effectively.", - "last_updated": "2025-05-17T10:08:45.172317Z", + "author_name": "Will", + "strategy_name": "SMA Crossover 1", + "description": "Goes long when the 18-period SMA crosses above the 80-period SMA, and exits when it crosses below.", + "last_updated": "2025-05-18T13:29:40.647678+00:00Z", "development_metrics": { - "sharpe": 1.4933060731407406, - "total_return": 31828.251724137932, - "max_drawdown": 0.9112345532958346, - "n_trades": 1, - "win_rate": 1.0 + "sharpe": 1.4162247381017314, + "total_return": 527047.6682905664, + "max_drawdown": 0.8147765465399606, + "n_trades": 922, + "win_rate": 0.4490238611713666 }, "holdout_metrics": { - "sharpe": 0.5471567498458149, - "total_return": 0.057312580028671345, - "max_drawdown": 0.3092850660964837, - "n_trades": 1, - "win_rate": 1.0 + "sharpe": 0.013786862738856922, + "total_return": -0.024336659763600776, + "max_drawdown": 0.25348362907002414, + "n_trades": 27, + "win_rate": 0.2962962962962963 } }, { - "author_name": "Genesis", + "author_name": "Lucien", "strategy_name": "SMA Crossover 1", - "description": "Goes long when the 25-period SMA crosses above the 150-period SMA, and exits when it crosses below.", - "last_updated": "2025-05-17T11:47:23.920022Z", + "description": "Goes long when the 32-period SMA crosses above the 140-period SMA, and exits when it crosses below.", + "last_updated": "2025-05-18T13:29:12.047768+00:00Z", "development_metrics": { - "sharpe": 1.3409691346166333, - "total_return": 52127.991594508945, - "max_drawdown": 0.8721222014401758, + "sharpe": 1.402672957918497, + "total_return": 281451.87029138196, + "max_drawdown": 0.7431645308660915, "n_trades": 505, - "win_rate": 0.4 + "win_rate": 0.39603960396039606 }, "holdout_metrics": { - "sharpe": -1.0977038161304256, - "total_return": -0.15928258447473653, - "max_drawdown": 0.37211232013725287, - "n_trades": 18, - "win_rate": 0.2222222222222222 + "sharpe": -0.7129619758797219, + "total_return": -0.11545206217806303, + "max_drawdown": 0.3235905435837149, + "n_trades": 19, + "win_rate": 0.21052631578947367 } }, { - "author_name": "Lucien", + "author_name": "Genesis", "strategy_name": "SMA Crossover 1", - "description": "Goes long when the 32-period SMA crosses above the 140-period SMA, and exits when it crosses below.", - "last_updated": "2025-05-17T09:58:22.770193Z", + "description": "Goes long when the 25-period SMA crosses above the 150-period SMA, and exits when it crosses below.", + "last_updated": "2025-05-18T13:28:30.814679+00:00Z", "development_metrics": { - "sharpe": 1.3255701716105417, - "total_return": 37176.1940346568, - "max_drawdown": 0.8976062164340162, + "sharpe": 1.4016624713245267, + "total_return": 245677.69310850097, + "max_drawdown": 0.761929316471299, "n_trades": 505, - "win_rate": 0.39603960396039606 + "win_rate": 0.4 }, "holdout_metrics": { - "sharpe": -0.692657754272795, - "total_return": -0.11414418233992363, - "max_drawdown": 0.2941198645359705, - "n_trades": 19, - "win_rate": 0.21052631578947367 + "sharpe": -1.0979785381365854, + "total_return": -0.1599624301040583, + "max_drawdown": 0.37391994324534034, + "n_trades": 18, + "win_rate": 0.2222222222222222 } }, { - "author_name": "Ben", - "strategy_name": "SMA Crossover 1 - f30s120", + "author_name": "Aditya", + "strategy_name": "SMA Crossover 1", "description": "Goes long when the 30-period SMA crosses above the 120-period SMA, and exits when it crosses below.", - "last_updated": "2025-05-17T09:58:25.545939Z", + "last_updated": "2025-05-18T13:27:41.479469+00:00Z", "development_metrics": { - "sharpe": 1.2890757652003817, - "total_return": 16908.019911407955, - "max_drawdown": 0.8924143378220439, + "sharpe": 1.3630880255669533, + "total_return": 105176.82201464486, + "max_drawdown": 0.7855955771199585, "n_trades": 584, "win_rate": 0.4126712328767123 }, "holdout_metrics": { - "sharpe": 0.1546100984967055, - "total_return": -0.005179828456650437, - "max_drawdown": 0.2720590455045794, + "sharpe": 0.194379280400519, + "total_return": 0.0005987785116801092, + "max_drawdown": 0.2451041192029137, "n_trades": 20, "win_rate": 0.25 } }, { - "author_name": "Aditya", - "strategy_name": "SMA Crossover 1", + "author_name": "Ben", + "strategy_name": "SMA Crossover 1 - f30s120", "description": "Goes long when the 30-period SMA crosses above the 120-period SMA, and exits when it crosses below.", - "last_updated": "2025-05-17T12:42:57.466976Z", + "last_updated": "2025-05-18T13:28:00.443237+00:00Z", "development_metrics": { - "sharpe": 1.2890757652003817, - "total_return": 16908.019911407955, - "max_drawdown": 0.8924143378220439, + "sharpe": 1.3630880255669533, + "total_return": 105176.82201464486, + "max_drawdown": 0.7855955771199585, "n_trades": 584, "win_rate": 0.4126712328767123 }, "holdout_metrics": { - "sharpe": 0.1546100984967055, - "total_return": -0.005179828456650437, - "max_drawdown": 0.2720590455045794, + "sharpe": 0.194379280400519, + "total_return": 0.0005987785116801092, + "max_drawdown": 0.2451041192029137, "n_trades": 20, "win_rate": 0.25 } }, { - "author_name": "Will", + "author_name": "Athon", "strategy_name": "SMA Crossover 1", - "description": "Goes long when the 18-period SMA crosses above the 80-period SMA, and exits when it crosses below.", - "last_updated": "2025-05-17T10:42:36.923447Z", + "description": "Goes long when the 20-period SMA crosses above the 100-period SMA, and exits when it crosses below.", + "last_updated": "2025-05-18T13:27:55.684620+00:00Z", "development_metrics": { - "sharpe": 1.269810403583702, - "total_return": 13939.800856186339, - "max_drawdown": 0.9369326634424754, - "n_trades": 922, - "win_rate": 0.4490238611713666 + "sharpe": 1.3587945434783149, + "total_return": 113118.12953676142, + "max_drawdown": 0.8755963724827027, + "n_trades": 780, + "win_rate": 0.40512820512820513 }, "holdout_metrics": { - "sharpe": -0.010999558421471817, - "total_return": -0.027846486707612583, - "max_drawdown": 0.25898048706982313, + "sharpe": -0.7014022187504372, + "total_return": -0.11715178226777567, + "max_drawdown": 0.30179458293070766, "n_trades": 27, - "win_rate": 0.2962962962962963 + "win_rate": 0.18518518518518517 } }, { - "author_name": "Lucien", - "strategy_name": "EMA Crossover + Adaptive ATR Filter", - "description": "Buy when fast EMA > slow EMA and ATR% > rolling quantile threshold; sell on reversal or low adaptive volatility.", - "last_updated": "2025-05-17T12:47:24.735129Z", + "author_name": "Adi, Mikey, Alex", + "strategy_name": "Z-Score Moon Mean Revert", + "description": "This PR implements the 'Crying Wolf' trading algorithm, a Z-score mean reversion strategy modulated by natural cyclic phenomena. Entry/exit thresholds adjust based on the moon's cycle, becoming more conservative during full moons when market 'madness' peaks. Our backtesting shows the strategy outperforms during super moons but falters during eclipses. Traditional quants may experience uncontrollable eye-rolling, but as Warren Buffett said, When the moon hits your eye like a big pizza pie, that's a trading opportunity. Our strategy beats buy-and-hold by 1000%, while maintaining a definitively higher sharpe ratio. May the moon shine over us all", + "last_updated": "2025-05-18T13:28:04.957185+00:00Z", "development_metrics": { - "sharpe": 1.217803722952385, - "total_return": 36432.64411560105, - "max_drawdown": 0.8861273181842388, - "n_trades": 2787, - "win_rate": 0.5331898098313599 + "sharpe": 1.2831520952536106, + "total_return": 19777.78533359002, + "max_drawdown": 0.766771035161839, + "n_trades": 8066, + "win_rate": 0.5090503347384081 }, "holdout_metrics": { - "sharpe": 1.2721023608824928, - "total_return": 0.11707790357354719, - "max_drawdown": 0.16707933054084675, - "n_trades": 76, - "win_rate": 0.5263157894736842 + "sharpe": 0.8776190469882273, + "total_return": 0.1032783521797469, + "max_drawdown": 0.1609747303078592, + "n_trades": 229, + "win_rate": 0.4847161572052402 + } + }, + { + "author_name": "Yuan", + "strategy_name": "Volume SMA Confirmation Strategy", + "description": "Goes long when the price breaks above the resistance with high volume, and exits when it breaks below the support with high volume.", + "last_updated": "2025-05-18T13:29:45.327338+00:00Z", + "development_metrics": { + "sharpe": 1.1788119422651215, + "total_return": 7889.140412874567, + "max_drawdown": 0.8298064510101139, + "n_trades": 735, + "win_rate": 0.48707482993197276 + }, + "holdout_metrics": { + "sharpe": 0.2667510523918981, + "total_return": 0.012254904930620425, + "max_drawdown": 0.22308333512674972, + "n_trades": 26, + "win_rate": 0.46153846153846156 } }, { "author_name": "Will", "strategy_name": "ML Enhanced Trading Strategy", "description": "A hybrid strategy using machine learning to select optimal parameters for technical indicators including SMA crossovers and RSI.", - "last_updated": "2025-05-17T12:54:19.621437Z", + "last_updated": "2025-05-18T13:29:32.500978+00:00Z", "development_metrics": { - "sharpe": 1.2090774290484267, - "total_return": 5993.580707097279, - "max_drawdown": 0.960077682257782, + "sharpe": 1.0977898937492188, + "total_return": 193.93862445695103, + "max_drawdown": 0.9712358814312182, "n_trades": 3079, "win_rate": 0.5849301721338097 }, "holdout_metrics": { - "sharpe": -0.3483303282506719, - "total_return": -0.06206203649176956, - "max_drawdown": 0.17887322097630512, + "sharpe": -0.3623844145786061, + "total_return": -0.06723510600819993, + "max_drawdown": 0.17690155664139906, "n_trades": 89, "win_rate": 0.4943820224719101 } }, { - "author_name": "Yuan", - "strategy_name": "Volume SMA Confirmation Strategy", - "description": "Goes long when the price breaks above the resistance with high volume, and exits when it breaks below the support with high volume.", - "last_updated": "2025-05-17T10:50:33.555705Z", + "author_name": "Genesis", + "strategy_name": "Volatility ATR Strategy", + "description": "Dynamic volatility-based strategy using ATR for entries, stops, and position sizing.", + "last_updated": "2025-05-18T13:28:35.343101+00:00Z", "development_metrics": { - "sharpe": 1.1497768598234075, - "total_return": 4483.2488594820325, - "max_drawdown": 0.8781365323919945, - "n_trades": 735, - "win_rate": 0.48707482993197276 + "sharpe": 1.0518634356403185, + "total_return": 0.7761309917070258, + "max_drawdown": 0.9970951700804799, + "n_trades": 6988, + "win_rate": 0.47510017172295366 }, "holdout_metrics": { - "sharpe": 0.7297079146266436, - "total_return": 0.07258730731958374, - "max_drawdown": 0.19649304246128135, - "n_trades": 26, - "win_rate": 0.46153846153846156 + "sharpe": 0.582187974595956, + "total_return": 0.058922131126614596, + "max_drawdown": 0.24611645156401185, + "n_trades": 209, + "win_rate": 0.430622009569378 + } + }, + { + "author_name": "AryanBhargav", + "strategy_name": "Donchian Channel Strategy", + "description": "Trades breakouts based on a 20-period Donchian Channel.", + "last_updated": "2025-05-18T13:27:45.985813+00:00Z", + "development_metrics": { + "sharpe": 1.040163090800165, + "total_return": 25.793359804370535, + "max_drawdown": 0.9959165586764145, + "n_trades": 1096, + "win_rate": 0.3841240875912409 + }, + "holdout_metrics": { + "sharpe": 0.7050265973276766, + "total_return": 0.07321305229549147, + "max_drawdown": 0.14185458087454178, + "n_trades": 34, + "win_rate": 0.4117647058823529 + } + }, + { + "author_name": "Lucien", + "strategy_name": "EMA Crossover + Adaptive ATR Filter", + "description": "Buy when fast EMA > slow EMA and ATR% > rolling quantile threshold; sell on reversal or low adaptive volatility.", + "last_updated": "2025-05-18T13:29:07.281570+00:00Z", + "development_metrics": { + "sharpe": 1.011750530263114, + "total_return": 226.85201862968057, + "max_drawdown": 0.9756139684066198, + "n_trades": 2787, + "win_rate": 0.5331898098313599 + }, + "holdout_metrics": { + "sharpe": 1.1866732966240807, + "total_return": 0.11206819740723217, + "max_drawdown": 0.1696016876885454, + "n_trades": 76, + "win_rate": 0.5263157894736842 } }, { "author_name": "Jim", "strategy_name": "Price Momentum", "description": "Buys when price increases from previous close, sells when it decreases, and holds otherwise.", - "last_updated": "2025-05-17T12:39:59.267829Z", + "last_updated": "2025-05-18T13:28:48.466491+00:00Z", "development_metrics": { - "sharpe": 0.276275037377082, - "total_return": 0.1333457776009599, - "max_drawdown": 1.0, + "sharpe": 0.8922038291984906, + "total_return": 4.408891741062862, + "max_drawdown": 0.9998266375001809, "n_trades": 31140, "win_rate": 0.48477842003853566 }, "holdout_metrics": { - "sharpe": 0.20767671433807, - "total_return": 0.007159277061369984, - "max_drawdown": 0.1572180057756682, + "sharpe": -0.22522156569994448, + "total_return": -0.05695868655450376, + "max_drawdown": 0.32383357778748956, "n_trades": 853, "win_rate": 0.47596717467760846 } + }, + { + "author_name": "YOUR_NAME", + "strategy_name": "YOUR_STRATEGY_NAME", + "description": "DESCRIBE YOUR STRATEGY HERE", + "last_updated": "2025-05-18T13:29:24.058039+00:00Z", + "development_metrics": { + "sharpe": 0.0, + "total_return": 0.0, + "max_drawdown": 0.0, + "n_trades": 0, + "win_rate": 0.0 + }, + "holdout_metrics": { + "sharpe": 0.0, + "total_return": 0.0, + "max_drawdown": 0.0, + "n_trades": 0, + "win_rate": 0.0 + } } ] } \ No newline at end of file diff --git a/scripts/update_leaderboard.py b/scripts/update_leaderboard.py index 67c3e4e..dafbfb4 100644 --- a/scripts/update_leaderboard.py +++ b/scripts/update_leaderboard.py @@ -7,7 +7,7 @@ import argparse from pathlib import Path import json -from datetime import datetime +from datetime import datetime, UTC import sys # Add src to Python path @@ -26,7 +26,7 @@ def update_leaderboard(strategy_path: str): "author_name": strategy.author_name, "strategy_name": strategy.strategy_name, "description": strategy.description, - "last_updated": datetime.utcnow().isoformat() + "Z" + "last_updated": datetime.now(UTC).isoformat() + "Z" } # Run backtests diff --git a/src/core/backtest.py b/src/core/backtest.py index 9bc7115..6470516 100644 --- a/src/core/backtest.py +++ b/src/core/backtest.py @@ -75,15 +75,16 @@ def run_backtest(strategy_class, df: pd.DataFrame, initial_capital: float = 1000 coins.iloc[i:] = current_coins elif exits.iloc[i]: # Exit position + equity_curve.iloc[i] = current_coins * df['close'].iloc[i] current_position = 0 current_coins = 0 coins.iloc[i:] = 0 + else: + equity_curve.iloc[i] = equity_curve.iloc[i-1] # Update equity curve if current_position == 1: equity_curve.iloc[i] = current_coins * df['close'].iloc[i] - else: - equity_curve.iloc[i] = equity_curve.iloc[i-1] if i > 0 else initial_capital # Generate trade records trades = []