Position Sizing and Risk Management: The Real Edge in Trading

Position sizing and risk management are the components of a trading system that determine the shape of your return distribution, while the signal only determines its drift. This distinction is the entire game. A positive-expectancy signal sized incorrectly is a negative-expectancy business once you account for the geometric cost of drawdowns and the non-zero probability of ruin. This article treats sizing as an optimization problem under a risk budget: how to convert a forecast into a position that maximizes long-run compound growth subject to surviving the worst plausible path.

The framing professionals use is geometric, not arithmetic. You do not get the average of your per-period returns; you get their compounded product, and compounding is ruthlessly punished by variance. Every sizing decision below is, ultimately, an attempt to control the variance drag and the left tail.

The geometry of drawdowns

Recovery from a drawdown is convex in the drawdown depth, which is why deep losses are categorically different from shallow ones:

DrawdownGain to recoverGeometric reality
10%11.1%Routine, ignorable
20%25.0%Uncomfortable
33%49.3%Serious
50%100%Must double remaining capital
75%300%Effectively career-ending
90%900%Unrecoverable

The required recovery is 1/(1-d) - 1, which diverges as d approaches 1. The practical implication is that protecting against the left tail is worth far more than squeezing extra return from the body of the distribution. See maximum drawdown for how to measure and constrain this directly, and risk of ruin for the probabilistic version.

Fixed fractional sizing

The baseline method risks a constant fraction of current equity per trade, with size derived from the distance to the stop:

def fixed_fractional_size(equity, risk_frac, entry, stop):
    """Units to trade so that hitting `stop` loses exactly risk_frac of equity."""
    risk_per_unit = abs(entry - stop)
    if risk_per_unit == 0:
        return 0
    return (equity * risk_frac) / risk_per_unit

Two properties make this the default. First, it harmonizes risk across setups: a wide stop yields a small position and a tight stop a large one, for identical dollar risk. Second, because risk is a fraction of current equity, sizing is geometric — you scale up after wins and automatically deleverage during a drawdown, a built-in defensive response. The cost is path dependence: the order of wins and losses affects the terminal outcome, which is exactly why you must stress the distribution of orderings rather than a single backtested path (below).

Volatility-based sizing

Fixed fractional sizing controls per-trade risk but not cross-asset risk contribution. Sizing inversely to volatility equalizes how much each position contributes to portfolio variance — the single-instrument analogue of risk parity:

import numpy as np

def vol_target_units(equity, target_ann_vol, price, ann_vol_est, point_value=1.0):
    """Size a position to a target annualized volatility contribution.

    target_ann_vol: e.g. 0.10 for 10% annualized risk from this sleeve
    ann_vol_est:    annualized volatility of the instrument's returns
    """
    notional_per_unit = price * point_value
    target_dollar_vol = equity * target_ann_vol
    instrument_dollar_vol = notional_per_unit * ann_vol_est
    if instrument_dollar_vol == 0:
        return 0.0
    return target_dollar_vol / instrument_dollar_vol

This prevents the classic error of allocating equal dollars to a placid bond future and a violent crypto perp, where the volatile leg then drives essentially all P&L variance. Volatility targeting at the strategy level — scaling gross exposure to hold realized portfolio volatility near a constant — is the same idea applied to the whole book and is the backbone of volatility-targeted drawdown control. A practical caveat: volatility estimates are themselves noisy and autocorrelated, so use a reasonable estimator (EWMA or a GARCH model) and cap leverage to avoid blowing up when the estimate collapses toward zero.

The Kelly criterion and why you fractionalize it

The Kelly criterion gives the fraction that maximizes long-run geometric growth. For a simple bet, f = W - (1 - W)/R, where W is win probability and R the win/loss ratio; for a continuous strategy with excess return mu and variance sigma^2, the optimal leverage is f* = mu / sigma^2. The expected log-growth at leverage f is approximately:

g(f) ≈ f * mu - 0.5 * f^2 * sigma^2

This is a downward parabola: growth rises, peaks at f, then falls, and past 2 f* it goes negative. So over-betting an edge you actually have still destroys capital. Three reasons practitioners use fractional Kelly (a quarter to a half):

  1. Parameter uncertainty. f* depends on mu, the least-estimable quantity in

finance. Overestimating mu pushes you past the peak, and the penalty is asymmetric — the downside of over-betting exceeds the upside of under-betting.

  1. Drawdown tolerance. Full Kelly routinely produces 50%+ peak-to-trough

declines. Half-Kelly captures roughly three-quarters of the growth rate at about half the volatility — a far better deal for anyone who must live through it.

  1. Non-stationarity. A static f* assumes a stable edge; real edges decay, so a

conservative fraction buys robustness.

Most disciplined fixed-fractional risk levels (1–2% per trade) land well below full Kelly, which is precisely why they survive.

Stops as a sizing input, not just an exit

The stop is the input to the size calculation, so the two decisions are inseparable. Place the stop where the trade thesis is genuinely invalidated, then derive size from it — never decide size first and reverse-engineer a stop to justify it, which inverts the logic and destroys risk control.

  • Volatility stops (a multiple of ATR or estimated sigma) adapt to the current

noise regime, so you are neither stopped out by ordinary wiggles in turbulence nor over-exposed in calm.

  • Structure stops sit beyond a swing level or

breakout point — the price at which the market has falsified your read.

  • Time stops acknowledge opportunity cost: capital in a trade going nowhere is

capital not deployed in a live edge.

Portfolio-level risk: the part beginners skip

Per-trade sizing is necessary but not sufficient, because trades are not independent. The dominant portfolio risk is correlation: ten 1%-risk longs in the same sector are not ten independent bets — they are approximately one 10% bet. Aggregate risk must be measured at the portfolio level, accounting for the covariance structure.

import numpy as np

def portfolio_risk(weights, cov):
    """Annualized portfolio volatility from weights and a covariance matrix."""
    w = np.asarray(weights, dtype=float)
    return float(np.sqrt(w @ np.asarray(cov) @ w))

def marginal_risk_contributions(weights, cov):
    """Each position's contribution to total portfolio volatility (sums to total)."""
    w = np.asarray(weights, dtype=float)
    cov = np.asarray(cov, dtype=float)
    port_vol = np.sqrt(w @ cov @ w)
    mrc = (cov @ w) / port_vol          # marginal contribution
    return w * mrc                       # component contribution

The component risk contributions reveal where your true exposure sits, which is frequently concentrated in a handful of correlated names even when nominal dollar weights look balanced. Beyond measurement, enforce hard limits: a gross/net exposure cap, a total "portfolio heat" budget, correlation clustering so correlated trades are sized as one, and a drawdown kill switch — a pre-committed rule to cut or halt trading at a defined loss. The kill switch exists because the worst decisions are made while trying to "win it back."

Stress-test the distribution, not the path

Your backtest realized exactly one ordering of wins and losses. The same trade set, reshuffled, can produce a far deeper drawdown. Monte Carlo resampling reveals the distribution of outcomes your sizing actually exposes you to:

import numpy as np

def mc_drawdown_quantiles(trade_returns, n=10_000, block=1):
    """Bootstrap max-drawdown distribution. Use block>1 to preserve autocorrelation."""
    r = np.asarray(trade_returns, dtype=float)
    worst = np.empty(n)
    for i in range(n):
        if block > 1:
            starts = np.random.randint(0, len(r) - block + 1, size=len(r) // block)
            path = np.concatenate([r[s:s + block] for s in starts])
        else:
            path = np.random.choice(r, size=len(r), replace=True)
        equity = np.cumprod(1 + path)
        dd = (equity - np.maximum.accumulate(equity)) / np.maximum.accumulate(equity)
        worst[i] = dd.min()
    return np.percentile(worst, [50, 95, 99])

Size so that even the 99th-percentile simulated drawdown is survivable both financially and psychologically. Use block bootstrap when returns are autocorrelated, since the naive IID shuffle understates clustered-loss drawdowns. If the 99th-percentile drawdown would force you to stop trading, your size is too large — full stop.

Honest limits

Risk management constrains the controllable; it does not eliminate the uncontrollable.

  • Stops do not bound loss in gaps. Overnight gaps, limit-down moves, and

liquidations can blow through a stop. Treat stop-implied risk as a best case and size for tail moves, especially with leverage.

  • Correlations are unstable and rise in crises. The diversification you measured

in calm markets partially evaporates exactly when you need it, so apply a haircut to estimated diversification benefit.

  • Volatility and Kelly inputs are estimates. Sizing built on noisy mu and

sigma inherits that noise; fractional Kelly and leverage caps are the defense.

  • Sizing cannot rescue a non-edge. Good risk control extends survival, but a

strategy with no real edge merely goes broke more slowly. Sizing buys you time to let a genuine edge express itself — nothing more.

The objective is not to maximize any single trade's return but to maximize the probability of still trading next year with capital intact. Combine fractional-Kelly- bounded sizing, volatility scaling, correlation-aware portfolio limits, a hard drawdown kill switch, and distribution-level stress testing, and you convert a fragile edge into a durable one. Pair it with honest backtesting and a clear-eyed respect for drawdowns and you have the foundation every lasting trading operation stands on.

#position sizing #risk management #money management #stop loss #trading psychology