Deep review of all indicator categories verified .md headers against .cs WarmupPeriod, parameters, inputs, and outputs. Fixes include warmup corrections, parameter documentation, output type accuracy, and Pine Script alignment.
5.5 KiB
CCI - Commodity Channel Index
| Property | Value |
|---|---|
| Category | Momentum |
| Inputs | OHLCV bar (TBar) |
| Parameters | period (default 20) |
| Outputs | Single series (CCI) |
| Output range | Varies (see docs) |
| Warmup | period bars |
TL;DR
- The Commodity Channel Index (CCI) is a versatile momentum-based oscillator developed by Donald Lambert in 1980.
- Parameterized by
period(default 20). - Output range: Varies (see docs).
- Requires
periodbars (20 default) of warmup before first valid output (IsHot = true). - Validated against TA-Lib, Skender, and Tulip reference implementations where available.
Overview
The Commodity Channel Index (CCI) is a versatile momentum-based oscillator developed by Donald Lambert in 1980. Originally designed for commodity trading, it measures the deviation of price from its statistical mean, normalized by mean absolute deviation.
Formula
TP = (High + Low + Close) / 3
SMA = Simple Moving Average of TP over period
Mean Deviation = SUM(|TP - SMA|) / period
CCI = (TP - SMA) / (0.015 × Mean Deviation)
Key Characteristics
| Property | Value |
|---|---|
| Default Period | 20 |
| Lambert Constant | 0.015 |
| Returns | Unbounded oscillator (typically -300 to +300) |
| Warmup Period | Equal to period |
| Input Data | OHLC bars (uses Typical Price) |
Signal Interpretation
Primary Levels
- Above +100: Strong uptrend, potentially overbought
- Below -100: Strong downtrend, potentially oversold
- Zero Line: Centerline crossover indicates trend change
Trading Strategies
- Trend Identification: Values consistently above/below zero indicate trend direction
- Overbought/Oversold: Extreme readings (+200/-200) suggest reversal potential
- Divergence: Price making new high/low while CCI fails to confirm
- Zero-Line Cross: Bullish when crossing above, bearish when crossing below
Lambert Constant (0.015)
The 0.015 constant was chosen by Lambert to ensure that approximately 70-80% of CCI values fall between +100 and -100 under normal market conditions. This provides a statistical framework where:
- Values outside ±100 indicate significant price movement
- Extended readings suggest strong trends
- Extreme values (±200 or beyond) are relatively rare
Usage
Basic Construction
// Create CCI with default 20-period
var cci = new Cci();
// Create CCI with custom period
var cci = new Cci(14);
Streaming Updates
foreach (var bar in realTimeData)
{
TValue result = cci.Update(bar);
double cciValue = result.Value;
if (cciValue > 100)
Console.WriteLine("Overbought territory");
else if (cciValue < -100)
Console.WriteLine("Oversold territory");
}
Batch Processing
TSeries results = Cci.Batch(barSeries, period: 20);
Comparison with Other Oscillators
| Indicator | Bounds | Best For |
|---|---|---|
| CCI | Unbounded | Trend strength, divergence |
| RSI | 0-100 | Overbought/oversold levels |
| Stochastic | 0-100 | Price position within range |
Historical Context
- Developed by Donald Lambert (1980)
- Originally published in Commodities magazine
- Early application for identifying cyclical trends in commodities
- Now widely used across all asset classes
References
- Lambert, D.R. (1980). "Commodity Channel Index: Tool for Trading Cyclic Trends"
- TradingView CCI Documentation
- Investopedia CCI Guide
Performance Profile
Operation Count (Streaming Mode)
Each Update() call on CCI(N) performs a full O(N) mean-deviation scan over the ring buffer. There is no closed-form running-sum decomposition for mean absolute deviation — the absolute values prevent the cancellation that makes SMA or variance incremental. The RingBuffer manages the sliding window; computing MAD requires visiting every element.
| Operation | Count | Cost (cycles) | Subtotal |
|---|---|---|---|
| Ring buffer push | 1 | 3 | ~3 |
| Running sum update (TP add/subtract) | 2 | 1 | ~2 |
| SMA divide | 1 | 8 | ~8 |
| MAD scan: N subtractions + N ABS | 2N | 2 | ~2N·2 |
| MAD divide | 1 | 8 | ~8 |
| Final scale + divide (0.015×MAD) | 2 | 3 | ~6 |
| Total | 2N + 7 | — | ~(4N + 27) cycles |
O(N) streaming cost per bar. For the default N = 20: ~107 cycles. No incremental shortcut exists for MAD; SIMD vectorization of the scan loop is the primary optimization lever.
Batch Mode (SIMD Analysis)
| Operation | Vectorizable? | Notes |
|---|---|---|
| Typical price (H+L+C)/3 | Yes | 3-wide FMA, AVX2 vectorizable |
| Rolling SMA via prefix sums | Yes | VADDPD on register array |
| MAD inner loop (ABS + accumulate) | Yes | VABSPD + VADDPD, width-8 per AVX2 lane |
| Final CCI scale | Yes | scalar multiply after reduction |
| State dependency across bars (SMA) | Partial | prefix sum removes dependency; MAD is fully independent per bar |
AVX2 processes 4 doubles per instruction. For the inner MAD loop of N=20, that is 5 SIMD passes vs 20 scalar iterations — roughly 3× throughput gain. The outer bar loop remains SIMD-friendly since each bar's TP is independent once the window positions are known.