Skip to main content

Overview

The ProphetCryptoPredictor class implements Meta’s (Facebook) Prophet algorithm, specialized for medium to long-term cryptocurrency price forecasting. Prophet excels at detecting trend changes and seasonal patterns in volatile time series data. Best for: Medium to long-term predictions (1 week to 1 month)

Constructor

from models.prophet_model import ProphetCryptoPredictor

predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.5,
    seasonality_prior_scale=10,
    interval_width=0.95
)

Parameters

changepoint_prior_scale
float
default:"0.5"
Controls flexibility in detecting trend changes. Higher values allow the model to fit more flexible trends.Effect on crypto:
  • Low (0.001-0.1): Conservative, smooth trends. Good for stable markets.
  • Medium (0.1-0.5): Balanced. Recommended for most crypto assets.
  • High (0.5-1.0): Highly flexible. Better for volatile altcoins.
Recommended range: 0.001-0.5Tuning guide:
  • Underfitting (too smooth)? Increase this value
  • Overfitting (too wiggly)? Decrease this value
seasonality_prior_scale
float
default:"10"
Controls strength of seasonal components (daily/weekly patterns).Effect:
  • Low (1-5): Weak seasonality, focuses more on trend
  • Medium (5-15): Balanced. Recommended for most cases.
  • High (15-30): Strong seasonality. Use if you see clear daily/weekly patterns.
Recommended range: 1-20
interval_width
float
default:"0.95"
Width of uncertainty intervals in predictions.Common values:
  • 0.80: 80% confidence (narrower bands)
  • 0.90: 90% confidence
  • 0.95: 95% confidence (wider bands, recommended)
  • 0.99: 99% confidence (very wide bands)
Recommended range: 0.8-0.95

Methods

prepare_data()

Converts DataFrame to Prophet’s required format (ds, y).
prophet_df = predictor.prepare_data(df)
df
pd.DataFrame
required
DataFrame with:
  • Datetime index
  • close column with price data
return
pd.DataFrame
DataFrame with Prophet format:
  • ds: Date/timestamp column
  • y: Price values (from close column)
NaN values are automatically removed.

train()

Trains the Prophet model on historical data.
metrics = predictor.train(df)

print(f"MAPE: {metrics['mape']:.2f}%")
print(f"Direction Accuracy: {metrics['direction_accuracy']:.2f}%")
print(f"Training Points: {metrics['training_points']}")
df
pd.DataFrame
required
Historical price data with datetime index and close column.Requirements:
  • Minimum 100 data points
  • Regular frequency (hourly or daily recommended)
  • No large gaps in time series
return
Dict
Dictionary with training metrics:
{
    'mae': float,                 # Mean Absolute Error
    'rmse': float,                # Root Mean Squared Error
    'mape': float,                # Mean Absolute Percentage Error (%)
    'direction_accuracy': float,  # Directional prediction accuracy (%)
    'training_points': int        # Number of data points used
}
Interpreting metrics:
  • mape: Lower is better (good: <10%, acceptable: <15% for crypto)
  • direction_accuracy: Higher is better (>50% = better than random)
  • rmse: Absolute error in price units

predict_future()

Generates forecasts with confidence intervals.
# Predict next 7 days (168 hours)
predictions = predictor.predict_future(periods=168, freq='H')

print(predictions)
#                      predicted_price  lower_bound  upper_bound    trend
# timestamp                           
# 2026-03-08 01:00:00      42500.32    40100.25    44900.39    42450.12
# 2026-03-08 02:00:00      42520.15    40080.33    44960.97    42470.08
# ...
periods
int
required
Number of time periods to forecast.Examples:
  • 168: 7 days (if freq=‘H’)
  • 720: 30 days (if freq=‘H’)
  • 7: 1 week (if freq=‘D’)
freq
str
default:"'H'"
Frequency of predictions.Common values:
  • 'H': Hourly
  • 'D': Daily
  • 'W': Weekly
Should match your training data frequency.
return
pd.DataFrame
DataFrame with datetime index and columns:
  • predicted_price (yhat): Point forecast
  • lower_bound (yhat_lower): Lower confidence interval
  • upper_bound (yhat_upper): Upper confidence interval
  • trend: Underlying trend component (without seasonality)
Note: Only returns future predictions (timestamps after last training date).

Utility Functions

backtest_prophet()

Performs time series cross-validation backtesting.
from models.prophet_model import backtest_prophet, ProphetCryptoPredictor

# Initialize predictor
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.3,
    seasonality_prior_scale=15
)

# Backtest with 1 week holdout
results = backtest_prophet(
    df, 
    predictor, 
    test_periods=168  # 1 week = 168 hours
)

print("Train Metrics:", results['train_metrics'])
print("Test Metrics:", results['test_metrics'])
print(f"Test MAPE: {results['test_metrics']['mape']:.2f}%")
df
pd.DataFrame
required
Historical OHLCV data with datetime index.
predictor
ProphetCryptoPredictor
required
Initialized predictor instance (not yet trained).
test_periods
int
default:"168"
Number of periods to hold out for testing.Common values:
  • 168: 1 week (hourly data)
  • 336: 2 weeks
  • 7: 1 week (daily data)
return
Dict
Comprehensive backtest results:
{
    'train_metrics': Dict,           # Metrics from training phase
    'test_metrics': {                # Metrics on held-out test set
        'mae': float,
        'rmse': float,
        'mape': float,
        'direction_accuracy': float
    },
    'train_actual': np.ndarray,      # Actual training prices
    'test_actual': np.ndarray,       # Actual test prices
    'test_predicted': np.ndarray,    # Predicted test prices
    'predictions': pd.DataFrame      # Full predictions DataFrame
}
Use test metrics to evaluate real-world performance.

Complete Example

import pandas as pd
from models.prophet_model import ProphetCryptoPredictor, backtest_prophet

# Load hourly Bitcoin data
df = pd.read_csv('btc_hourly.csv', index_col='timestamp', parse_dates=True)

print(f"Data shape: {df.shape}")
print(f"Date range: {df.index[0]} to {df.index[-1]}")

# Initialize predictor with optimized parameters
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.3,    # Medium flexibility
    seasonality_prior_scale=12,      # Moderate seasonality
    interval_width=0.95              # 95% confidence intervals
)

# Train on full dataset
print("\nTraining Prophet model...")
metrics = predictor.train(df)

print(f"\nTraining Results:")
print(f"  MAE: ${metrics['mae']:.2f}")
print(f"  RMSE: ${metrics['rmse']:.2f}")
print(f"  MAPE: {metrics['mape']:.2f}%")
print(f"  Direction Accuracy: {metrics['direction_accuracy']:.2f}%")

# Predict next 30 days (720 hours)
print("\nGenerating 30-day forecast...")
predictions = predictor.predict_future(periods=720, freq='H')

print(f"\nForecast Summary:")
print(f"  Start: {predictions.index[0]}")
print(f"  End: {predictions.index[-1]}")
print(f"  Predicted price at end: ${predictions['predicted_price'].iloc[-1]:.2f}")
print(f"  Confidence range: ${predictions['lower_bound'].iloc[-1]:.2f} - ${predictions['upper_bound'].iloc[-1]:.2f}")

# Analyze trend
trend_change = predictions['trend'].iloc[-1] - predictions['trend'].iloc[0]
print(f"  Trend direction: {'Upward' if trend_change > 0 else 'Downward'}")
print(f"  Trend change: ${abs(trend_change):.2f}")

# Save predictions
predictions.to_csv('prophet_predictions_30d.csv')
print("\nPredictions saved to prophet_predictions_30d.csv")

# Optional: Perform backtesting
print("\n" + "="*50)
print("BACKTESTING WITH 2-WEEK HOLDOUT")
print("="*50)

backtest_predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.3,
    seasonality_prior_scale=12,
    interval_width=0.95
)

backtest_results = backtest_prophet(
    df, 
    backtest_predictor, 
    test_periods=336  # 2 weeks
)

print(f"\nBacktest Results (2-week holdout):")
print(f"  Test MAPE: {backtest_results['test_metrics']['mape']:.2f}%")
print(f"  Test Direction Accuracy: {backtest_results['test_metrics']['direction_accuracy']:.2f}%")
print(f"  Test RMSE: ${backtest_results['test_metrics']['rmse']:.2f}")

Model Configuration Guide

Configuration for Prophet

The Prophet model includes several built-in configurations:
self.model = Prophet(
    changepoint_prior_scale=changepoint_prior_scale,  # Your parameter
    seasonality_prior_scale=seasonality_prior_scale,  # Your parameter
    interval_width=interval_width,                    # Your parameter
    daily_seasonality=True,        # Captures 24-hour patterns
    weekly_seasonality=True,       # Captures 7-day patterns
    yearly_seasonality=False,      # Disabled (crypto too volatile)
    seasonality_mode='multiplicative'  # Better for crypto price data
)

Tuning for Different Cryptocurrencies

Bitcoin (BTC) / Ethereum (ETH) - Large Cap:
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.2,   # More stable, less volatile
    seasonality_prior_scale=10,
    interval_width=0.95
)
Volatile Altcoins:
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.5,   # More flexible for rapid changes
    seasonality_prior_scale=15,    # Stronger seasonal patterns
    interval_width=0.95
)
Bull Market (trending up):
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.3,
    seasonality_prior_scale=8,     # Less seasonality, more trend
    interval_width=0.90
)
Bear Market / Sideways:
predictor = ProphetCryptoPredictor(
    changepoint_prior_scale=0.15,  # Less aggressive trend changes
    seasonality_prior_scale=15,    # More weight on patterns
    interval_width=0.95
)

Key Characteristics

Strengths:
  • Excellent for trend detection and long-term forecasting
  • Automatically handles seasonality (daily/weekly patterns)
  • Built-in confidence intervals
  • Robust to missing data and outliers
  • Interpretable components (trend, seasonality)
  • Handles changepoints (sudden trend shifts) automatically
Limitations:
  • Slower training than XGBoost
  • Not ideal for very short-term predictions (<24 hours)
  • Requires minimum 100 data points
  • Less effective in highly erratic markets
  • Cannot use external features/regressors in this implementation
Typical Performance:
  • MAPE: 5-12% for 7-day predictions
  • Direction Accuracy: 52-60%
  • Best for: 3-day to 30-day forecasts
When to Use Prophet:
  • Forecasting 1 week to 1 month ahead
  • Need confidence intervals
  • Want to understand trend vs. seasonality
  • Historical data shows clear patterns
  • Presenting forecasts to non-technical stakeholders

Build docs developers (and LLMs) love