Files
QuanTAlib/lib/trends/tema/Tema.md
T
2025-12-18 13:51:06 -08:00

131 lines
4.2 KiB
Markdown

# TEMA: Triple Exponential Moving Average
## What It Does
The Triple Exponential Moving Average (TEMA) is a technical indicator designed to smooth price data while virtually eliminating the lag associated with traditional moving averages. By combining a single, double, and triple Exponential Moving Average (EMA), TEMA creates a composite line that tracks price action with remarkable speed and accuracy.
## Historical Context
Developed by Patrick Mulloy and introduced in his 1994 article "Smoothing Data with Faster Moving Averages" in *Technical Analysis of Stocks & Commodities*, TEMA was created alongside DEMA (Double EMA) to solve the persistent problem of lag in trend-following indicators. Mulloy's innovation was to use the lag inherent in multiple EMA calculations to estimate and subtract the total lag from the original signal.
## How It Works
### The Core Idea
TEMA is not just "an EMA of an EMA of an EMA" (which would be very slow). Instead, it uses a clever formula to cancel out lag:
- $EMA_1$ has some lag.
- $EMA_2$ (EMA of EMA) has roughly double the lag.
- $EMA_3$ (EMA of EMA of EMA) has roughly triple the lag.
By combining these terms with specific weights ($3 \times EMA_1 - 3 \times EMA_2 + EMA_3$), the lag terms cancel out, leaving a moving average that hugs the price closely.
### Mathematical Foundation
$$ TEMA = (3 \times EMA_1) - (3 \times EMA_2) + EMA_3 $$
Where:
- $EMA_1 = EMA(Price)$
- $EMA_2 = EMA(EMA_1)$
- $EMA_3 = EMA(EMA_2)$
### Implementation Details
Our implementation uses three internal EMA instances.
- **Complexity:** O(1) per update.
- **Initialization:** We use Hunter's method for initializing the underlying EMAs to ensure the TEMA starts with valid values as early as possible.
## Configuration
| Parameter | Default | Purpose | Adjustment Guidelines |
|-----------|---------|---------|----------------------|
| Period | 14 | Lookback window | Short (5-10) for scalping; Medium (20-50) for swing trading. |
## Performance Profile
| Operation | Complexity | Description |
|-----------|------------|-------------------|
| Streaming update | O(1) | 3 EMA updates + scalar math |
| Bar correction | O(1) | Efficient state rollback |
| Batch processing | O(N) | Single pass through data |
| Memory footprint | O(1) | Stores state for 3 internal EMAs |
## Interpretation
### Trading Signals
#### Trend Direction
- **Fast Response:** TEMA turns much faster than SMA or EMA. A turn in TEMA often precedes a turn in price trend.
#### Crossovers
- **Price Crossover:** Because TEMA hugs price so closely, crossovers are frequent. They are best used for short-term entries in the direction of a larger trend.
### When It Works Best
- **Momentum Trading:** TEMA is excellent for capturing short-term bursts of momentum.
### When It Struggles
- **Overshoot:** In a sudden V-shaped reversal, TEMA can "overshoot" the price briefly due to the momentum of its internal calculation components.
## Architecture Notes
This implementation makes specific trade-offs:
### Choice: Composition
- **Implementation:** Composed of 3 `Ema` objects.
- **Rationale:** Reusing the robust `Ema` class ensures consistent behavior (like initialization and NaN handling) across the library.
## References
- Mulloy, Patrick G. "Smoothing Data with Faster Moving Averages." *Technical Analysis of Stocks & Commodities*, Jan 1994.
## C# Usage
### Streaming Updates (Single Instance)
```csharp
using QuanTAlib;
var tema = new Tema(period: 14);
// Process each new bar
TValue result = tema.Update(new TValue(timestamp, closePrice));
Console.WriteLine($"TEMA: {result.Value:F2}");
// Check if buffer is full
if (tema.IsHot)
{
// Indicator is fully initialized
}
```
### Batch Processing (Historical Data)
```csharp
// TSeries API
TSeries prices = ...;
TSeries temaValues = Tema.Batch(prices, period: 14);
// Span API (High Performance)
double[] prices = new double[1000];
double[] output = new double[1000];
Tema.Calculate(prices.AsSpan(), output.AsSpan(), period: 14);
```
### Bar Correction (isNew Parameter)
```csharp
var tema = new Tema(14);
// New bar
tema.Update(new TValue(time, 100), isNew: true);
// Intra-bar update
tema.Update(new TValue(time, 101), isNew: false); // Replaces 100 with 101