Article-22714-Volatility-Mo.../Include/slsqp_article/Arch/Univariate/base.mqh

349 lines
12 KiB
MQL5
Raw Permalink Normal View History

2026-06-03 20:14:05 +02:00
//+------------------------------------------------------------------+
//| base.mqh |
//| Copyright 2025, MetaQuotes Ltd. |
//| https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2025, MetaQuotes Ltd."
#property link "https://www.mql5.com"
#include"..\..\np.mqh"
#include"..\Utility\wald.mqh"
#include"..\..\Regression\OLS.mqh"
#include"..\..\Regression\utils.mqh"
//---
#define EMPTY_VECTOR vector::Zeros(0)
#define EMPTY_MATRIX matrix::Zeros(0,0)
//---
vector EMPTY_VECTOR_ARRAY[];
matrix EMPTY_MATRIX_ARRAY[];
//+------------------------------------------------------------------+
//| covariance type |
//+------------------------------------------------------------------+
enum ENUM_COVAR_TYPE
{
COVAR_CLASSIC = 0,//classic
COVAR_ROBUST//robust
};
//+------------------------------------------------------------------+
//| forecasting method |
//+------------------------------------------------------------------+
enum ENUM_FORECAST_METHOD
{
FORECAST_ANALYTIC=0,//analytic
FORECAST_SIMULATION,//simulation
FORECAST_BOOTSTRAP//bootstrap
};
//+------------------------------------------------------------------+
//| forecast alignment |
//+------------------------------------------------------------------+
enum ENUM_FORECAST_ALIGNMENT
{
ALIGN_ORIGIN = 0,//origin
ALIGN_TARGET//target
};
//+------------------------------------------------------------------+
//| mean models |
//+------------------------------------------------------------------+
enum ENUM_MEAN_MODEL
{
MEAN_CONSTANT=0,//Constant Mean
MEAN_ZERO,//Zero Mean
MEAN_AR,//AR
MEAN_ARX,//AR-X
MEAN_HAR,//HAR
MEAN_HARX//HAR-X
};
//---
const string MEAN_MODELS = "Constant Mean,Zero Mean,AR,AR-X,HAR,HAR-X";
//+------------------------------------------------------------------+
//| volatility models |
//+------------------------------------------------------------------+
enum ENUM_VOLATILITY_MODEL
{
VOL_CONST=0,//Constant Variance
VOL_ARCH,//ARCH
VOL_AVARCH,//AVARCH
VOL_AVGARCH,//AVGARCH
VOL_TARCH,//TARCH ZARCH
VOL_GARCH,//GARCH
VOL_GJR_GARCH//GJR_GARCH
};
//---
const string VOLATILITY_MODELS = "Constant Variance,ARCH,AVARCH,AVGARCH,TARCH ZARCH,GARCH,GJR GARCH";
//+------------------------------------------------------------------+
//| distributions |
//+------------------------------------------------------------------+
enum ENUM_DISTRIBUTION_MODEL
{
DIST_NORMAL=0,//Normal
DIST_STUDENT,//Standardized Student's T
DIST_SKEW_STUDENT,//Standardized Skew Student's T
DIST_GEN_ERROR,//Generalized Error Distribution
};
//---
const string DISTRIBUTIONS = "Normal,Standardized Student's t,Standardized Skew Student's t,Generalized Error Distribution";
//+------------------------------------------------------------------+
//|Test a matrix for an implicit constant |
//+------------------------------------------------------------------+
bool implicit_constant(matrix &exog_data)
{
ulong nobs = exog_data.Rows();
matrix temp(nobs,exog_data.Cols()+1);
vector ones = vector::Ones(nobs);
temp.Col(ones,0);
for(ulong i = 1; i<temp.Cols(); ++i)
temp.Col(exog_data.Col(i-1),i);
ulong rank = temp.Rank();
return (rank == exog_data.Cols());
}
//+------------------------------------------------------------------+
//|reindex |
//+------------------------------------------------------------------+
bool _reindex(ulong actual, matrix& in[], matrix& out[])
{
ulong obs = ulong(in.Size());
if(actual>obs)
{
ArrayResize(out,int(actual));
matrix temp = matrix::Zeros(in[0].Rows(),in[0].Cols());
temp.Fill(EMPTY_VALUE);
for(uint i = 0; i<uint(actual - obs); ++i)
out[i] = (i<uint(actual - obs))?temp:in[i-uint(actual - obs)];
}
return true;
}
//+------------------------------------------------------------------+
//|reindex |
//+------------------------------------------------------------------+
matrix _reindex(ulong actual, matrix& in)
{
ulong obs = ulong(in.Rows());
if(actual>obs)
{
matrix out(actual);
vector temp = vector::Zeros(in.Cols());
temp.Fill(EMPTY_VALUE);
for(ulong i = 0; i<(actual - obs); ++i)
out.Row((i<(actual - obs))?temp:in.Row(i-(actual - obs)),i);
return out;
}
return in;
}
//+------------------------------------------------------------------+
//|reindex |
//+------------------------------------------------------------------+
vector _reindex(ulong actual, vector& in)
{
ulong obs = ulong(in.Size());
if(actual>obs)
{
vector out(actual);
double temp = EMPTY_VALUE;
for(ulong i = 0; i<(actual - obs); ++i)
out[i] = (i<(actual - obs))?temp:in[i-(actual - obs)];
return out;
}
return in;
}
//+------------------------------------------------------------------+
//| generate parameter names |
//+------------------------------------------------------------------+
string common_names(ulong p, ulong o, ulong q)
{
string names = "omega";
for(ulong i = 0; i<p; ++i)
names += ",alpha["+string(i+1)+"]";
for(ulong i = 0; i<o; ++i)
names += ",gamma["+string(i+1)+"]";
for(ulong i = 0; i<q; ++i)
names += ",beta["+string(i+1)+"]";
return names;
}
//+------------------------------------------------------------------+
//| Arch parameters |
//+------------------------------------------------------------------+
struct ArchParameters
{
// --- Data & Core Configuration
vector observations;
matrix exog_data;
vector mean_lags;
ENUM_MEAN_MODEL mean_model_type;
ENUM_VOLATILITY_MODEL vol_model_type;
ENUM_DISTRIBUTION_MODEL dist_type;
ulong holdout_size;
bool is_rescale_enabled;
double scaling_factor;
// --- Mean Model Parameters
bool include_constant;
bool use_har_rotation;
// --- Volatility Process Parameters (GARCH/ARCH)
int vol_rng_seed;
ulong garch_p;
ulong garch_o;
ulong garch_q;
double vol_power;
long sample_start_idx;
long sample_end_idx;
ulong min_bootstrap_sims;
// --- Distribution Parameters
vector dist_init_params;
int dist_rng_seed;
ArchParameters(void)
{
observations = vector::Zeros(0);
exog_data = matrix::Zeros(0,0);
mean_lags = vector::Zeros(0);
vol_model_type=WRONG_VALUE;
dist_type=WRONG_VALUE;
holdout_size=0;
scaling_factor = 1.0;
is_rescale_enabled=false;
mean_model_type = WRONG_VALUE;
include_constant = true;
use_har_rotation =false;
vol_rng_seed = 0;
garch_p = 1;
garch_o = 0;
garch_q = 1;
vol_power=2.;
sample_start_idx=1;
sample_end_idx=-1;
min_bootstrap_sims=100;
dist_init_params = vector::Zeros(0);
dist_rng_seed = 0;
}
ArchParameters(ArchParameters &other)
{
observations = other.observations;
exog_data = other.exog_data;
scaling_factor = other.scaling_factor;
mean_lags = other.mean_lags;
vol_model_type=other.vol_model_type;
dist_type=other.dist_type;
holdout_size=other.holdout_size;
is_rescale_enabled=other.is_rescale_enabled;
include_constant = other.include_constant;
use_har_rotation = other.use_har_rotation;
vol_rng_seed = other.vol_rng_seed;
garch_p = other.garch_p;
garch_o = other.garch_o;
garch_q = other.garch_q;
vol_power=other.vol_power;
sample_start_idx=other.sample_start_idx;
sample_end_idx=other.sample_end_idx;
min_bootstrap_sims=other.min_bootstrap_sims;
dist_init_params = other.dist_init_params;
dist_rng_seed = other.dist_rng_seed;
}
void operator=(ArchParameters &other)
{
observations = other.observations;
exog_data = other.exog_data;
scaling_factor = other.scaling_factor;
mean_lags = other.mean_lags;
vol_model_type=other.vol_model_type;
dist_type=other.dist_type;
holdout_size=other.holdout_size;
is_rescale_enabled=other.is_rescale_enabled;
include_constant = other.include_constant;
use_har_rotation = other.use_har_rotation;
vol_rng_seed = other.vol_rng_seed;
garch_p = other.garch_p;
garch_o = other.garch_o;
garch_q = other.garch_q;
vol_power=other.vol_power;
sample_start_idx=other.sample_start_idx;
sample_end_idx=other.sample_end_idx;
min_bootstrap_sims=other.min_bootstrap_sims;
dist_init_params = other.dist_init_params;
dist_rng_seed = other.dist_rng_seed;
}
};
//+------------------------------------------------------------------+
//| arch simulation |
//+------------------------------------------------------------------+
struct ArchSimulation
{
matrix values[];
matrix residuals[];
matrix variances[];
matrix residual_variances[];
ArchSimulation(void)
{
}
ArchSimulation(matrix& _values[],matrix& _residuals[], matrix& _variances[], matrix& _residual_variances[])
{
np::copy3D(_values,values);
np::copy3D(_residuals,residuals);
np::copy3D(_variances,variances);
np::copy3D(_residual_variances,residual_variances);
}
ArchSimulation(ArchSimulation &other)
{
np::copy3D(other.values,values);
np::copy3D(other.residuals,residuals);
np::copy3D(other.variances,variances);
np::copy3D(other.residual_variances,residual_variances);
}
void operator=(ArchSimulation &other)
{
np::copy3D(other.values,values);
np::copy3D(other.residuals,residuals);
np::copy3D(other.variances,variances);
np::copy3D(other.residual_variances,residual_variances);
}
};
//+------------------------------------------------------------------+
//| arch forecast result |
//+------------------------------------------------------------------+
struct ArchForecast
{
matrix mean;
matrix variance;
matrix residual_variance;
ArchSimulation simulation;
ArchForecast(void)
{
mean = variance = residual_variance = matrix::Zeros(0,0);
}
ArchForecast(ulong startindex, matrix& _mean, matrix& _variance, matrix& _res_var, matrix& _values[], matrix& _residuals[], matrix& _variances[], matrix& _residual_variances[])
{
mean = _mean;
variance = _variance;
residual_variance = _res_var;
np::copy3D(_values,simulation.values);
np::copy3D(_residuals,simulation.residuals);
np::copy3D(_variances,simulation.variances);
np::copy3D(_residual_variances,simulation.residual_variances);
}
ArchForecast(ArchForecast &other)
{
mean = other.mean;
variance = other.variance;
residual_variance = other.residual_variance;
simulation = other.simulation;
}
void operator=(ArchForecast &other)
{
mean = other.mean;
variance = other.variance;
residual_variance = other.residual_variance;
simulation = other.simulation;
}
};
//+------------------------------------------------------------------+