test on original data

This commit is contained in:
Vasily.onl 2025-05-26 14:55:03 +08:00
parent 3e94387dcb
commit b1f80099fe

View File

@ -28,6 +28,7 @@ from cycles.strategies.default_strategy import DefaultStrategy
from cycles.IncStrategies.indicators.supertrend import SupertrendState, SupertrendCollection from cycles.IncStrategies.indicators.supertrend import SupertrendState, SupertrendCollection
from cycles.Analysis.supertrend import Supertrends from cycles.Analysis.supertrend import Supertrends
from cycles.backtest import Backtest from cycles.backtest import Backtest
from cycles.utils.storage import Storage
# Configure logging # Configure logging
logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s') logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
@ -44,6 +45,7 @@ class MetaTrendComparisonTest:
self.test_data = None self.test_data = None
self.original_results = None self.original_results = None
self.incremental_results = None self.incremental_results = None
self.storage = Storage(logging=logger)
# Supertrend parameters from original implementation # Supertrend parameters from original implementation
self.supertrend_params = [ self.supertrend_params = [
@ -52,34 +54,44 @@ class MetaTrendComparisonTest:
{"period": 11, "multiplier": 2.0} {"period": 11, "multiplier": 2.0}
] ]
def load_test_data(self, symbol: str = "BTCUSDT", limit: int = 500) -> pd.DataFrame: def load_test_data(self, symbol: str = "BTCUSD", start_date: str = "2022-01-01", end_date: str = "2023-01-01", limit: int = None) -> pd.DataFrame:
""" """
Load test data for comparison. Load test data for comparison using the Storage class.
Args: Args:
symbol: Trading symbol to load symbol: Trading symbol to load (used for filename)
limit: Number of data points to load start_date: Start date in YYYY-MM-DD format
end_date: End date in YYYY-MM-DD format
limit: Optional limit on number of data points (applied after date filtering)
Returns: Returns:
DataFrame with OHLCV data DataFrame with OHLCV data
""" """
logger.info(f"Loading test data for {symbol} (limit: {limit})") logger.info(f"Loading test data for {symbol} from {start_date} to {end_date}")
try: try:
# Try to load from existing data files # Use the Storage class to load data with date filtering
data_file = f"data/{symbol}_1m.csv" filename = "btcusd_1-min_data.csv"
if os.path.exists(data_file):
df = pd.read_csv(data_file)
df['timestamp'] = pd.to_datetime(df['timestamp'])
df.set_index('timestamp', inplace=True)
df = df.tail(limit)
logger.info(f"Loaded {len(df)} data points from {data_file}")
else:
# Generate synthetic data for testing if no real data available
logger.warning(f"No data file found at {data_file}, generating synthetic data")
df = self._generate_synthetic_data(limit)
# Ensure required columns # Convert date strings to pandas datetime
start_dt = pd.to_datetime(start_date)
end_dt = pd.to_datetime(end_date)
# Load data using Storage class
df = self.storage.load_data(filename, start_dt, end_dt)
if df.empty:
raise ValueError(f"No data found for the specified date range: {start_date} to {end_date}")
logger.info(f"Loaded {len(df)} data points from {start_date} to {end_date}")
logger.info(f"Date range in data: {df.index.min()} to {df.index.max()}")
# Apply limit if specified
if limit is not None and len(df) > limit:
df = df.tail(limit)
logger.info(f"Limited data to last {limit} points")
# Ensure required columns (Storage class should handle column name conversion)
required_cols = ['open', 'high', 'low', 'close', 'volume'] required_cols = ['open', 'high', 'low', 'close', 'volume']
for col in required_cols: for col in required_cols:
if col not in df.columns: if col not in df.columns:
@ -92,12 +104,20 @@ class MetaTrendComparisonTest:
df_with_timestamp = df.reset_index() df_with_timestamp = df.reset_index()
self.test_data = df_with_timestamp self.test_data = df_with_timestamp
logger.info(f"Test data prepared: {len(df_with_timestamp)} rows")
logger.info(f"Columns: {list(df_with_timestamp.columns)}")
logger.info(f"Sample data:\n{df_with_timestamp.head()}")
return df_with_timestamp return df_with_timestamp
except Exception as e: except Exception as e:
logger.error(f"Failed to load test data: {e}") logger.error(f"Failed to load test data: {e}")
# Fallback to synthetic data import traceback
df = self._generate_synthetic_data(limit) traceback.print_exc()
# Fallback to synthetic data if real data loading fails
logger.warning("Falling back to synthetic data generation")
df = self._generate_synthetic_data(limit or 1000)
df_with_timestamp = df.reset_index() df_with_timestamp = df.reset_index()
self.test_data = df_with_timestamp self.test_data = df_with_timestamp
return df_with_timestamp return df_with_timestamp
@ -681,13 +701,15 @@ class MetaTrendComparisonTest:
return timeline_df return timeline_df
def run_full_test(self, symbol: str = "BTCUSDT", limit: int = 500) -> bool: def run_full_test(self, symbol: str = "BTCUSD", start_date: str = "2022-01-01", end_date: str = "2023-01-01", limit: int = None) -> bool:
""" """
Run the complete comparison test. Run the complete comparison test.
Args: Args:
symbol: Trading symbol to test symbol: Trading symbol to test
limit: Number of data points to test start_date: Start date in YYYY-MM-DD format
end_date: End date in YYYY-MM-DD format
limit: Optional limit on number of data points (applied after date filtering)
Returns: Returns:
True if all tests pass, False otherwise True if all tests pass, False otherwise
@ -698,7 +720,7 @@ class MetaTrendComparisonTest:
try: try:
# Load test data # Load test data
self.load_test_data(symbol, limit) self.load_test_data(symbol, start_date, end_date, limit)
logger.info(f"Test data loaded: {len(self.test_data)} points") logger.info(f"Test data loaded: {len(self.test_data)} points")
# Test original strategy # Test original strategy
@ -760,35 +782,21 @@ def main():
"""Run the MetaTrend comparison test.""" """Run the MetaTrend comparison test."""
test = MetaTrendComparisonTest() test = MetaTrendComparisonTest()
# Run test with different data sizes # Run test with real BTCUSD data from 2022-01-01 to 2023-01-01
test_cases = [ logger.info(f"\n{'='*80}")
("BTCUSDT", 200), # Small test logger.info(f"RUNNING METATREND COMPARISON TEST")
("BTCUSDT", 500), # Medium test logger.info(f"Using real BTCUSD data from 2022-01-01 to 2023-01-01")
("BTCUSDT", 1000), # Large test logger.info(f"{'='*80}")
]
all_passed = True # Test with the full year of data (no limit)
passed = test.run_full_test("BTCUSD", "2022-01-01", "2023-01-01", limit=None)
for symbol, limit in test_cases: if passed:
logger.info(f"\n{'='*80}") logger.info("\n🎉 TEST PASSED! Incremental indicators match original strategy.")
logger.info(f"RUNNING TEST CASE: {symbol} with {limit} data points")
logger.info(f"{'='*80}")
passed = test.run_full_test(symbol, limit)
all_passed = all_passed and passed
if not passed:
logger.error(f"Test case {symbol}:{limit} FAILED")
break
else:
logger.info(f"Test case {symbol}:{limit} PASSED")
if all_passed:
logger.info("\n🎉 ALL TEST CASES PASSED!")
else: else:
logger.error("\nSOME TEST CASES FAILED!") logger.error("\n❌ TEST FAILED! Incremental indicators do not match original strategy.")
return all_passed return passed
if __name__ == "__main__": if __name__ == "__main__":