You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

GARCH模型与神经网络的时间序列建模对比及实施建议咨询

Comparing GARCH vs. Neural Networks for FX Rate Time Series Modeling

Hey there! You’ve already got a solid GARCH model set up for your scaled foreign exchange rate data—great start. Let’s walk through how to build a comparable neural network and rigorously compare the two models’ performance. Here’s a step-by-step breakdown tailored to your workflow:

1. Align Your Modeling Target First

Your GARCH model is focused on volatility modeling (since you’re using include.mean=FALSE in the mean model). To make a fair comparison, your neural network should also target volatility prediction (not just raw price forecasting). If you intended to predict prices instead, you’ll need to adjust your GARCH setup to include a mean component, but let’s stick with volatility for now since that’s your current GARCH focus.

First, make sure you’re working with returns (not raw scaled prices) for both models—GARCH is designed for return volatility. If you haven’t already, calculate log returns from your scaled prices:

# Calculate log returns from your scaled currency data
currency_returns <- diff(log(currency))
# Drop NA values from the first difference
currency_returns <- na.omit(currency_returns)

2. Prepare Time-Series Data for Neural Networks

Time-series data can’t be randomly split like cross-sectional data—you need to preserve temporal order. Use a time-based split:

  • 70% for training
  • 15% for validation (to tune neural network hyperparameters)
  • 15% for testing (final performance comparison)

You’ll also need to create lagged features (since neural networks don’t inherently understand time order). For volatility prediction, common inputs include:

  • Lagged returns
  • Lagged volatility estimates (e.g., rolling window standard deviations, or even your GARCH model’s past predictions)
  • Lagged price changes

Here’s an example of creating lagged features for an LSTM (a popular neural network for time series) in R using the keras package:

library(keras)
library(zoo)

# Function to create lagged features and reshape for LSTM
prepare_lstm_data <- function(volatility_series, lag_steps = 5) {
  # Create lagged columns
  lagged_df <- data.frame(vol = volatility_series)
  for (i in 1:lag_steps) {
    lagged_df[[paste0("lag_", i)]] <- lag(lagged_df$vol, i)
  }
  # Remove rows with NA values from lagging
  lagged_df <- na.omit(lagged_df)
  
  # Split into input (X) and target (y)
  X <- lagged_df[, -1]
  y <- lagged_df[, 1]
  
  # Reshape X to 3D array required for LSTM: (samples, time steps, features)
  X <- array_reshape(X, c(nrow(X), lag_steps, 1))
  
  list(X = X, y = y)
}

# Calculate "true" volatility using a rolling window (for comparison)
true_volatility <- rollapply(currency_returns, width = 5, FUN = sd, align = "right", fill = NA)
true_volatility <- na.omit(true_volatility)

# Prepare LSTM data
lstm_dataset <- prepare_lstm_data(true_volatility, lag_steps = 5)

# Time-based split
train_idx <- floor(0.7 * nrow(lstm_dataset$X))
val_idx <- floor(0.85 * nrow(lstm_dataset$X))

X_train <- lstm_dataset$X[1:train_idx,,]
y_train <- lstm_dataset$y[1:train_idx]
X_val <- lstm_dataset$X[(train_idx+1):val_idx,,]
y_val <- lstm_dataset$y[(train_idx+1):val_idx]
X_test <- lstm_dataset$X[(val_idx+1):nrow(lstm_dataset$X),,]
y_test <- lstm_dataset$y[(val_idx+1):nrow(lstm_dataset$y)]

3. Build & Train the Neural Network

For time-series volatility prediction, LSTMs or GRUs are solid choices (they handle sequential dependencies well). Here’s a basic LSTM implementation:

# Build the LSTM model
lstm_model <- keras_model_sequential() %>%
  layer_lstm(units = 32, input_shape = c(5, 1), return_sequences = FALSE) %>%
  layer_dropout(rate = 0.2) %>%  # Add dropout to prevent overfitting
  layer_dense(units = 1)

# Compile the model
lstm_model %>% compile(
  optimizer = optimizer_adam(learning_rate = 0.001),
  loss = "mse"  # Mean Squared Error works for volatility, but QLIKE is also common
)

# Train with early stopping to avoid overfitting
early_stopping <- callback_early_stopping(monitor = "val_loss", patience = 5, restore_best_weights = TRUE)

history <- lstm_model %>% fit(
  X_train, y_train,
  epochs = 50,
  batch_size = 32,
  validation_data = list(X_val, y_val),
  callbacks = list(early_stopping)
)

If you want to try a simpler model first, you could use a feedforward neural network (MLP) with lagged features—just skip the 3D reshaping step.

4. Generate Predictions from Both Models

First, get volatility predictions from your trained GARCH model on the test set:

# Extract GARCH volatility predictions for the test period
# Assuming your test set starts at index (val_idx+1) of the original returns
garch_test_preds <- predict(garch_fit, n.ahead = length(y_test), newdata = currency_returns[(val_idx+1 - length(true_volatility)):(length(currency_returns))])
garch_vol_preds <- as.numeric(garch_test_preds@forecast$sigmaFor)

Then get predictions from your neural network:

# LSTM predictions on test set
lstm_test_preds <- lstm_model %>% predict(X_test)
lstm_test_preds <- as.numeric(lstm_test_preds)

5. Rigorously Compare Model Performance

Don’t just rely on in-sample fit—focus on out-of-sample test set performance, since that’s what matters for real-world use. Use these metrics:

Quantitative Metrics

  • RMSE/MAE: Standard error metrics for comparing prediction accuracy.
  • QLIKE Loss: A more robust metric for volatility prediction (since volatility is positive and heteroskedastic):
    qlike_loss <- function(true, pred) {
      mean(log(pred) + (true^2)/pred)
    }
    
  • Diebold-Mariano Test: Statistically tests whether one model’s predictions are significantly better than the other:
    library(forecast)
    dm_test <- dm.test(y_test - garch_vol_preds, y_test - lstm_test_preds, h = 1)
    print(dm_test)
    

Visual Comparison

Plot the true volatility alongside both models’ predictions to see how they track trends:

library(ggplot2)

comparison_df <- data.frame(
  Time = seq_along(y_test),
  True_Vol = y_test,
  GARCH_Pred = garch_vol_preds,
  LSTM_Pred = lstm_test_preds
)

ggplot(comparison_df, aes(x = Time)) +
  geom_line(aes(y = True_Vol, color = "True Volatility"), linewidth = 1) +
  geom_line(aes(y = GARCH_Pred, color = "GARCH Prediction"), linetype = "dashed") +
  geom_line(aes(y = LSTM_Pred, color = "LSTM Prediction"), linetype = "dotted") +
  labs(title = "Volatility Prediction Comparison", x = "Time Step", y = "Volatility") +
  scale_color_manual(values = c("True Volatility" = "black", "GARCH Prediction" = "blue", "LSTM Prediction" = "red")) +
  theme_minimal()

6. Next Steps to Refine & Validate

  • Hyperparameter Tuning: For the neural network, test different lag lengths, unit counts, dropout rates, or even model architectures (e.g., GRU, Temporal Fusion Transformer).
  • Feature Engineering: Add external features like interest rate differentials, inflation data, or other currency returns to see if they boost performance.
  • Hybrid Models: Try combining GARCH predictions as an input feature to the neural network, or averaging predictions from both models—sometimes hybrid approaches outperform single models.
  • Robustness Checks: Test with different train/validation/test splits, or use rolling window forecasting (instead of a single split) to ensure your results aren’t dependent on one specific time period.

Hope this helps you run a thorough, meaningful comparison between your GARCH and neural network models!

内容的提问来源于stack exchange,提问作者Jackie Vazquez

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 03:49:05