Median Price

Haiyue
11min

I. What is Median Price

Median Price, also known as Midpoint Price, is the arithmetic mean of the high and low prices of each bar. It represents the geometric center of the price range for each bar.

Historical Background

Median Price is one of the most fundamental price transforms in technical analysis, with a history nearly as old as candlestick and bar charts themselves. In technical analysis literature from the late 19th to early 20th century, analysts were already using the midpoint of High and Low to simplify price data.

This concept was formally referenced in J. Welles Wilder’s classic work New Concepts in Technical Trading Systems (1978), where it served as the calculation basis for multiple indicators. Since then, many technical indicators (such as Average True Range variants and channel indicators) have used Median Price as a price input.

Indicator Classification

  • Type: Overlay indicator, plotted directly on the price chart
  • Category: Other Overlay / Price Transform
  • Default Parameters: No parameters; calculated independently for each bar
  • Data Requirements: Requires only High and Low data
The Meaning of “Median”

Although the name uses “Median,” the calculation of Median Price is actually an arithmetic mean, not a statistical median. The “Median” here refers to the “midpoint” of the price range — the middle position between the high and low prices.


II. Mathematical Principles and Calculation

Core Formula

The Median Price formula is very straightforward:

MPt=Ht+Lt2MP_t = \frac{H_t + L_t}{2}

Where:

  • HtH_t is the high price of bar tt
  • LtL_t is the low price of bar tt

Step-by-Step Calculation

  1. Obtain the high and low prices: These two prices define the price range [Lt,Ht][L_t, H_t] for the bar.
  2. Calculate the average: Add High and Low, then divide by 2 to get the center of the range.
  3. Calculate per bar: Each bar completes the above steps independently.

Geometric Interpretation

Median Price can be understood from several perspectives:

  • Range midpoint: It is the exact center of the bar’s price range Rt=HtLtR_t = H_t - L_t
  • Equidistant property: The distance from MPtMP_t to HtH_t equals the distance from MPtMP_t to LtL_t, both being Rt2\frac{R_t}{2}
  • Range positioning: Any OHLC price can be expressed as the Median Price plus an offset

MPtLt=HtMPt=HtLt2=Rt2MP_t - L_t = H_t - MP_t = \frac{H_t - L_t}{2} = \frac{R_t}{2}

Relationship with Candlestick Patterns

The relative position of Median Price to the close price can reveal candlestick pattern characteristics:

  • Ct>MPtC_t > MP_t — Close is in the upper half, bar is bullish-leaning
  • Ct<MPtC_t < MP_t — Close is in the lower half, bar is bearish-leaning
  • CtMPtC_t \approx MP_t — Close is near the middle, bulls and bears are balanced
Close Position Ratio

A normalized indicator can be defined: Position=CtLtHtLtPosition = \frac{C_t - L_t}{H_t - L_t}. When Position > 0.5, the close is above the Median Price. This is essentially the core concept behind many oscillators (such as Williams %R and Stochastic Oscillator).


III. Python Implementation

import numpy as np
import pandas as pd

def median_price(high: pd.Series, low: pd.Series) -> pd.Series:
    """
    Calculate Median Price

    Parameters
    ----------
    high : pd.Series
        High price series
    low : pd.Series
        Low price series

    Returns
    -------
    pd.Series
        Median price series
    """
    result = (high + low) / 2.0
    result.name = "MedianPrice"
    return result


def median_price_numpy(high: np.ndarray, low: np.ndarray) -> np.ndarray:
    """
    Calculate Median Price using numpy
    """
    return (high + low) / 2.0


# ========== Usage Example ==========
if __name__ == "__main__":
    np.random.seed(42)
    dates = pd.date_range("2024-01-01", periods=100, freq="D")
    price = 100 + np.cumsum(np.random.randn(100) * 0.5)

    df = pd.DataFrame({
        "date": dates,
        "open":  price + np.random.randn(100) * 0.2,
        "high":  price + np.abs(np.random.randn(100) * 0.7),
        "low":   price - np.abs(np.random.randn(100) * 0.7),
        "close": price + np.random.randn(100) * 0.15,
        "volume": np.random.randint(1000, 10000, size=100),
    })
    df.set_index("date", inplace=True)

    # Calculate Median Price
    df["median_price"] = median_price(df["high"], df["low"])

    # Calculate close price position relative to Median Price
    df["close_position"] = (df["close"] - df["low"]) / (df["high"] - df["low"])

    # Print results
    print("=== Median Price vs Close Comparison (Last 15 Days) ===")
    print(df[["high", "low", "close", "median_price", "close_position"]].tail(15))

    # Statistical analysis
    above = (df["close"] > df["median_price"]).sum()
    below = (df["close"] < df["median_price"]).sum()
    print(f"\nDays with close above Median Price: {above}")
    print(f"Days with close below Median Price: {below}")
    print(f"Bull/Bear ratio: {above/below:.2f}")

    # Use Median Price as input for moving averages
    df["MP_SMA_20"] = df["median_price"].rolling(window=20).mean()
    df["Close_SMA_20"] = df["close"].rolling(window=20).mean()

    print("\n=== SMA(20) Based on Median Price ===")
    print(df[["close", "median_price", "MP_SMA_20", "Close_SMA_20"]].tail(10))

    # Signal example: close crossing above Median Price SMA
    df["signal"] = np.where(df["close"] > df["MP_SMA_20"], 1,
                   np.where(df["close"] < df["MP_SMA_20"], -1, 0))
    cross = df["signal"].diff().abs() > 0
    print("\nCrossover signal points:")
    print(df.loc[cross, ["close", "MP_SMA_20", "signal"]].tail(10))

IV. Problems the Indicator Solves

1. Determining the Center of Price Fluctuations

Median Price precisely identifies the center of the price range for each bar. When analyzing market structure, this center point represents the “bull-bear equilibrium point” better than the open or close:

  • Consecutive days with rising Median Price indicate the overall price range is shifting upward, suggesting an uptrend
  • Consecutive days with falling Median Price indicate the overall price range is shifting downward, suggesting a downtrend

2. Building Channel and Range Indicators

Median Price serves as the foundation for many channel indicators:

  • Donchian Channel midline: Essentially the nn-period version of Median Price
  • Keltner Channel: Built on Median Price or Typical Price
  • Any indicator system requiring a “midline” can use Median Price as the baseline

3. Filtering Open and Close Noise

Open and close prices are susceptible to short-term dynamics (such as opening auctions and end-of-day anomalies). Median Price uses only High and Low, avoiding the pricing noise from open/close and more purely reflecting the intraday price fluctuation center.

4. Quick Bull/Bear Strength Assessment

Comparing the close price with Median Price is a quick method for assessing the bullish or bearish tendency of a bar:

ConditionInterpretation
C>MPC > MP (close in upper half)Bulls dominated the day
C<MPC < MP (close in lower half)Bears dominated the day
O>MPO > MP and C<MPC < MPBulls lost ground, bearish reversal
O<MPO < MP and C>MPC > MPBears lost ground, bullish reversal
Note

Median Price completely ignores close and open price information. In markets with frequent opening gaps or closing anomalies (such as Chinese A-shares), relying solely on Median Price may miss important price information.


V. Advantages, Disadvantages, and Use Cases

Advantages

AdvantageDescription
Extremely simpleRequires only two data points (High, Low) and one operation
No parametersNo parameter selection or optimization issues
Good noise resistanceUnaffected by abnormal volatility during open/close sessions
Clear geometric meaningPrecise midpoint of the price range, intuitively easy to understand

Disadvantages

DisadvantageDescription
Incomplete informationUses only 2 prices, discarding Open and Close information
Sensitive to extreme barsExtremely long upper or lower shadows will pull MP toward extremes
Ignores closing consensusClose is the market’s final consensus, but MP completely ignores it
No independent signalsDoes not generate any trading signals on its own

Use Cases

  • As input price source: Substitute MP for Close when you need to avoid open/close noise in indicator inputs
  • Channel indicator construction: Serves as the midline baseline for upper and lower channel boundaries
  • Bull/bear strength analysis: Use the relative position of Close to MP as an auxiliary bull/bear assessment
  • Simplified data scenarios: When only High/Low data is available (some historical data sources provide only these two prices)

Comparison with Other Price Types

ComparisonMedian PriceAverage PriceTypical Price
Data requirementsH, LO, H, L, CH, L, C
Close influenceNone25%33%
Open noise resistanceStrongWeakStrong
Extreme shadow sensitivityHighMediumMedium
Common usageChannel midlineGeneral substituteCCI/MFI input
Practical Tips
  1. When building custom channel indicators, Median Price is the most natural midline choice because it is inherently the center of the price range.
  2. Continuously observing the direction of deviation between Median Price and close price can identify the market’s “closing tendency” — consistently closing above MP is a bullish signal.
  3. Using the moving average of Median Price as a trend assessment standard is smoother than directly using the moving average of Close.
  4. If your strategy frequently triggers false signals at High/Low extremes, you may need to switch to Typical Price or Average Price.