17 using System.Collections.Generic;
37 private readonly List<int> _timeLags;
42 private readonly decimal _sumX;
47 private readonly decimal _sumX2;
56 public HurstExponent(
string name,
int period,
int maxLag = 20) : base(name)
60 throw new ArgumentException(
"The maxLag parameter must be greater than 2 to compute the Hurst Exponent.", nameof(maxLag));
63 _timeLags =
new List<int>();
66 for (var i = 2; i < maxLag; i++)
68 var logTimeLag = (decimal)Math.Log(i);
71 _sumX2 += logTimeLag * logTimeLag;
83 : this($
"HE({period},{maxLag})", period, maxLag)
95 public override bool IsReady => _priceWindow.IsReady;
104 _priceWindow.Add(input.
Value);
105 if (!_priceWindow.IsReady)
116 foreach (var lag
in _timeLags)
119 var sumOfSquares = 0m;
120 var count = Math.Max(0, _priceWindow.Size - lag);
122 for (var i = 0; i < count; i++)
124 var value = _priceWindow[i + lag] - _priceWindow[i];
125 sumOfSquares += value * value;
129 var standardDeviation = 0.0;
134 var variance = (sumOfSquares / count) - (mean * mean);
135 standardDeviation = Math.Sqrt((
double)variance);
139 var logTau = standardDeviation == 0.0 ? 0m : (decimal)Math.Log(standardDeviation);
140 var logLag = (decimal)Math.Log(lag);
144 sumXY += logLag * logTau;
148 var n = _timeLags.Count;
151 var hurstExponent = (n * sumXY - _sumX * sumY) / (n * _sumX2 - _sumX * _sumX);
152 return hurstExponent;
160 _priceWindow.Reset();