Trading Dev AcademyFree quant education

Free lesson · Time series

Autocorrelation: momentum, mean reversion, or coin flips

Open interactive lessonPractice calculationsExplore labs

Start with the idea

Autocorrelation asks whether past deviations line up with later deviations. The sign can suggest continuation or reversal at a chosen lag, but the same series can have different signs at different horizons.

Symbols, units & horizon
  • xₜ: observation at time t
  • x̄: full-sample mean
  • n: observation count
  • k: lag in periods
  • ρ_k: sample autocorrelation at lag k
  • φ: coefficient of zero-mean AR(1)
  • εₜ: unpredictable innovation
  • |φ|: absolute decay coefficient
  • ln: natural logarithm
  • h or half-life: number of periods for expected shock magnitude to halve

When and why to use this

Use ACF as a diagnostic for forecastable dependence and for invalid IID standard errors. Use estimated half-life to compare a reversion thesis with holding costs and execution latency.

The autocorrelation at lag k is the correlation of a series with itself k steps ago:

ρk=∑t=k+1n(xt−x‾)(xt−k−x‾)∑t=1n(xt−x‾)2
Algebra and arithmetic

Compute sample autocorrelation

  1. Centre the series using its sample mean. Multiply each deviation by the deviation k observations earlier and sum over overlapping pairs.
  2. Divide by the full squared-deviation sum. This is the biased ACF convention shown here; other normalisations differ in small samples. The approximate white-noise band scales as 1.96n.
Work it by hand

For x=(1,2,1,2), mean 1.5 and denominator 1. Lag-one products sum to −.75; estimated ρ₁=−.75.

ρ₁ of returnsbehaviourthe trade
> 0momentum — moves continuebuy strength, sell weakness
< 0mean reversion — moves reversefade extremes
≈ 0random walkno timing edge at this horizon

Under the null of no autocorrelation, sample ρk is approximately normal with standard deviation 1n. Bars outside ±1.96n are "significant". With 250 daily returns the band is ±0.12; a lag-1 autocorrelation of 0.05 in daily equity returns — which is about what exists — is invisible at that sample size and only becomes tradeable with thousands of observations or many assets.

ARIMA: the grammar of linear forecasting

AR(p) says today depends on the last p values; MA(q) says today depends on the last q shocks; I(d) says difference d times first to make the series stationary. The AR(1) case is the workhorse:

xt=ϕxt−1+εt,half-life of a shock=ln⁡0.5ln⁡|ϕ|
Algebra and arithmetic

Solve an autoregressive shock half-life

  1. Ignoring future mean-zero innovations, a deviation d becomes ϕhd after h periods. Its magnitude halves when |ϕ|h=12.
  2. Take logs: hln⁡|ϕ|=ln⁡(12), then divide. Require 0<|φ|<1. A negative φ alternates direction; φ=0 removes the conditional deviation in one step.
Work it by hand

φ=.8 gives h=ln(.5)/ln(.8)=3.106 periods. φ=.5 gives exactly one period.

ϕ close to 1 means shocks persist (near random walk). ϕ close to 0 means fast reversion. The half-life is the natural holding period for a mean-reversion trade on that series — it converts a statistical parameter into a decision.

A spread follows AR(1) with ϕ=0.9 on daily data. Half-life in days?

ln⁡0.5ln⁡0.9=−0.693−0.105=6.6. Expect to hold about a week for half the deviation to close; two weeks for three-quarters.

Python implementation

Self-contained teaching example. Python 3.10+; dependencies and input conventions are shown in the code and notation. Run in your own Python environment.

from statistics import mean
from math import log

def acf(values, lag):
    if not 0 <= lag < len(values):
        raise ValueError("Lag outside sample")
    centered = [x-mean(values) for x in values]
    denominator = sum(x*x for x in centered)
    if denominator == 0:
        raise ValueError("ACF undefined for constant series")
    return sum(centered[t]*centered[t-lag] for t in range(lag,len(values)))/denominator

def shock_half_life(phi):
    if not 0 < abs(phi) < 1:
        raise ValueError("Require 0 < |phi| < 1")
    return log(.5)/log(abs(phi))

print(shock_half_life(.8))

Continue learning

Time Series Analysis — all lessons
  1. Start with time order, lags and differences
  2. Before GARCH: mean, shocks and changing variance
  3. Stationarity: the assumption every test makes and every market breaks
  4. Autocorrelation: momentum, mean reversion, or coin flips
  5. GARCH: volatility clusters, and you can model the cluster
  6. Cointegration: a stationary relationship to test
  7. Forecast horizons, EWMA, and model diagnostics
  8. Markov chains: a two-state model you can calculate by hand
  9. Hidden Markov models: predict, observe, update

Quantitative finance and development glossary · Python resources and libraries · Research sources and limitations