Kelly Criterion Position Sizing, Measured
The Kelly criterion sets bet size from your edge. See what ten years of daily stock returns imply about full Kelly, drawdown, and half Kelly in practice.
The Kelly criterion is a formula for bet size. Feed it a probability of winning, the size of a win, and the size of a loss, and it returns the fraction of capital that maximizes the long run growth rate of wealth. John Kelly published it at Bell Labs in 1956 as an information-theory result, and gamblers and traders adopted it afterward. This page walks the formula from first principles, then measures what it prescribes on ten years of real daily stock returns, where the prescription turns out to be unlivable.
What the Kelly criterion actually says
Take a repeated bet that wins a fraction g of the amount staked with probability p, and loses a fraction l of the amount staked with probability q, where q is one minus p. The growth-optimal fraction of capital to commit on each repetition is:
f* = p / l - q / g
In the classic even-money case, where a win pays what a loss costs, g and l both equal 1 and the formula collapses to f* = p - q. That difference is the edge itself. A wager that wins 60% of the time at even money carries a 20-point edge, and Kelly stakes 20% of the bankroll on it.
The derivation is a single step of calculus applied to the expected logarithm of wealth. Maximizing the average log of wealth per bet is equivalent to maximizing the compound growth rate over a long sequence, and the fraction that achieves it is the one above. Two properties fall out of that. Kelly never stakes the entire bankroll on a bet that can lose everything, since the logarithm of zero is negative infinity. And any fixed fraction other than f, repeated long enough, compounds more slowly than f does.
A coin flip you can check by hand
The figures in this section are hypothetical, chosen to make the arithmetic visible. Take a coin that lands heads 60% of the time and pays even money, with a starting bankroll of $1,000.
- Stake 20% of the bankroll on every flip. A win carries $1,000 to $1,200; a loss carries it to $800. One win and one loss, in either order, leaves $960.
- Stake 40% of the bankroll on every flip. The same win-then-loss pair runs $1,000 to $1,400 to $840.
- Stake the whole bankroll on every flip. A single tail ends the sequence permanently, whatever the edge was.
That 4% round-trip cost at 20% staking is the price of compounding a volatile bankroll, and a 60/40 coin covers it many times over across a long sequence. At 40% staking the round-trip cost is 16%, and the coin no longer covers it: the growth rate at twice the Kelly fraction lands at roughly zero. Past that point a bet with a genuine, verified edge grows nothing at all, which is the most useful single fact the formula carries.
What the formula asks for on a daily stock bet
Now point the same formula at a market. Treat one trading day in one stock as one repetition of the bet: the win probability is the share of days that closed up, the win size is the average up-day move, and the loss size is the average down-day move. Ten full calendar years of daily closes, 2016 through 2025, across six familiar names:
The exact SQL behind every number
WITH daily AS (
SELECT ticker,
toDate(toTimeZone(window_start, 'America/New_York')) AS dt,
argMax(toFloat64(close), window_start) AS c
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker IN ('SPY', 'KO', 'JNJ', 'MSFT', 'NVDA', 'TSLA')
AND window_start >= '2016-01-01 00:00:00'
AND window_start < '2026-01-01 00:00:00'
AND (toHour(toTimeZone(window_start, 'America/New_York')) * 60
+ toMinute(toTimeZone(window_start, 'America/New_York'))) BETWEEN 570 AND 959
GROUP BY ticker, dt
),
steps AS (
SELECT ticker, dt, c,
lagInFrame(c) OVER (PARTITION BY ticker ORDER BY dt
ROWS BETWEEN 1 PRECEDING AND CURRENT ROW) AS prev
FROM daily
),
rets AS (
SELECT ticker, c / prev - 1 AS ret
FROM steps
WHERE prev > 0 AND c != prev
)
SELECT ticker,
round(100 * countIf(ret > 0) / count(), 1) AS win_rate_pct,
round(100 * avgIf(ret, ret > 0), 2) AS avg_gain_pct,
round(100 * abs(avgIf(ret, ret < 0)), 2) AS avg_loss_pct,
round(countIf(ret > 0) / count() / abs(avgIf(ret, ret < 0))
- countIf(ret < 0) / count() / avgIf(ret, ret > 0), 1) AS full_kelly_x
FROM rets
GROUP BY ticker
HAVING countIf(ret > 0) > 0 AND countIf(ret < 0) > 0
ORDER BY full_kelly_x DESCRead the first three columns and the edge looks tiny. Win rates cluster near a coin flip, and the average up day and the average down day are close in size for every name in the panel. SPY closed higher on 55.3% of its sessions, gaining 0.71% on an average up day against 0.76% on an average down day.
The last column is where the trouble starts. Those small, nearly balanced inputs sit in the denominators of the formula, and small denominators produce large answers. The fraction the formula returns for SPY is 10.1 times capital, and the lowest of the 6 names still lands at 2 times. Full Kelly on a daily equity bet is not a percentage of the account. It is a demand for leverage that no broker extends and no account survives.
The shape of the tradeoff
That is the theory. The next panel is the experiment. Take the actual daily returns of the S&P 500 tracker over the same ten years, scale each day's return by a fixed bet size, and compound the result. A bet size of 1.0x is the unlevered index. A bet size of 3.0x commits three dollars for every dollar of capital, every day, rebalanced daily. Each row is one full ten-year path, with its ending wealth and the deepest peak-to-trough fall it took along the way.
The exact SQL behind every number
WITH daily AS (
SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS dt,
argMax(toFloat64(close), window_start) AS c
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker = 'SPY'
AND window_start >= '2016-01-01 00:00:00'
AND window_start < '2026-01-01 00:00:00'
AND (toHour(toTimeZone(window_start, 'America/New_York')) * 60
+ toMinute(toTimeZone(window_start, 'America/New_York'))) BETWEEN 570 AND 959
GROUP BY dt
),
steps AS (
SELECT dt, c,
lagInFrame(c) OVER (ORDER BY dt ROWS BETWEEN 1 PRECEDING AND CURRENT ROW) AS prev
FROM daily
),
rets AS (
SELECT dt, c / prev - 1 AS ret
FROM steps
WHERE prev > 0
),
sizes AS (
SELECT arrayJoin([0.5, 1.0, 1.5, 2.0, 2.5, 3.0, 4.0, 5.0]) AS bet
),
paths AS (
SELECT bet, dt,
exp(sum(log(greatest(1 + bet * ret, 0.0001)))
OVER (PARTITION BY bet ORDER BY dt
ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW)) AS equity
FROM rets CROSS JOIN sizes
),
peaks AS (
SELECT bet, dt, equity,
max(equity) OVER (PARTITION BY bet ORDER BY dt
ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS peak
FROM paths
)
SELECT concat(toString(bet), 'x') AS bet_size,
round(argMax(equity, dt), 2) AS ending_multiple,
round(100 * max(1 - equity / peak), 1) AS max_drawdown_pct
FROM peaks
GROUP BY bet
ORDER BY betAt 0.5x the path ended at 1.92 times its starting capital, with a worst fall of 18.2% from a prior high. At 5x, the same daily returns and the same decade, the path ended at 14.35 times, with a worst fall of 94.5%.
The two columns move differently, and that is the whole lesson of fractional Kelly. Ending wealth rises with bet size for a while, flattens, and then turns down as the drag from compounding volatility overtakes the extra exposure. The drawdown column has no such turning point. It climbs at every step across the 8 rows, and it climbs faster than the wealth column ever did. Half of the growth of the optimal bet is available at half the optimal bet size, at a small fraction of the pain. That asymmetry is the argument for staking less than f*, and it is why the half-Kelly convention exists at all.
The estimate is the weak part, not the formula
The formula is exact for a bet whose odds are known. In a casino the odds are printed. In a market they are estimated from history, and the estimate wobbles. Here is the same calculation as the first panel, run separately on each of the ten calendar years for a single index tracker.
The exact SQL behind every number
WITH daily AS (
SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS dt,
argMax(toFloat64(close), window_start) AS c
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker = 'SPY'
AND window_start >= '2016-01-01 00:00:00'
AND window_start < '2026-01-01 00:00:00'
AND (toHour(toTimeZone(window_start, 'America/New_York')) * 60
+ toMinute(toTimeZone(window_start, 'America/New_York'))) BETWEEN 570 AND 959
GROUP BY dt
),
steps AS (
SELECT dt, c,
lagInFrame(c) OVER (ORDER BY dt ROWS BETWEEN 1 PRECEDING AND CURRENT ROW) AS prev
FROM daily
),
rets AS (
SELECT dt, c / prev - 1 AS ret
FROM steps
WHERE prev > 0 AND c != prev
)
SELECT toString(toYear(dt)) AS year,
round(100 * countIf(ret > 0) / count(), 1) AS win_rate_pct,
round(100 * avgIf(ret, ret > 0), 2) AS avg_gain_pct,
round(100 * abs(avgIf(ret, ret < 0)), 2) AS avg_loss_pct,
round(countIf(ret > 0) / count() / abs(avgIf(ret, ret < 0))
- countIf(ret < 0) / count() / avgIf(ret, ret > 0), 1) AS full_kelly_x
FROM rets
GROUP BY year
HAVING countIf(ret > 0) > 0 AND countIf(ret < 0) > 0
ORDER BY yearEvery row is an estimate of the same unknown quantity, built from roughly 250 observations. Year 2016 returned 13.7, on a win rate of 53.8%. Year 2025 returned 12.3, on a win rate of 57.8%. The chart shows how far apart 10 readings of one number can land when each is drawn from a single year.
That dispersion matters more than any refinement of the formula. Overstate your edge by a factor of two and the formula hands back roughly twice the bet size, which places you at or past the point where growth turns negative. Understate it and you give up growth you could have compounded, at no risk of ruin. The two errors are not symmetric, and the cheap side of the asymmetry is the small side. Practitioners who use Kelly at all tend to stake half of it, or a quarter, and treat the formula as a ceiling rather than a target.
Where the model stops describing a market
Kelly assumes a bet you can repeat with fixed, known odds, and outcomes that are independent from one repetition to the next. A market breaks all of that. Odds are estimated and change over time. Daily returns cluster: quiet stretches follow quiet stretches, and violent days arrive in groups, which stretches drawdowns beyond what an independence assumption predicts. Positions are not settled at the end of each day, gaps skip past the price where a bet would have been closed, and margin calls arrive on the schedule of the broker rather than the schedule of the model.
The formula still earns its keep as a boundary. It states, in one line, that there is a bet size past which more conviction produces less wealth, and it locates that boundary from quantities a trader can at least attempt to measure. That is also why the same logic points toward diversification: several partly independent bets share the same total risk budget more efficiently than one bet does, which is the arithmetic underneath concentration risk. And for an investor adding money on a schedule rather than sizing discrete wagers, the position-sizing question is answered by the schedule itself, which is the case for dollar-cost averaging.
FAQ
What is the Kelly criterion formula?
For a bet that wins a fraction g of the stake with probability p and loses a fraction l with probability q, the growth-optimal fraction of capital is f = p / l - q / g. In the even-money case it simplifies to f = p - q, the edge itself.
Why do traders use half Kelly instead of full Kelly?
Growth is close to flat near the optimum while risk keeps rising past it, so cutting the bet in half surrenders a modest amount of long-run growth and removes a large share of the drawdown. Estimation error compounds the argument: a doubled bet from an overstated edge sits near the point where growth stops.
Does the Kelly criterion work for stocks?
It applies as arithmetic, and its assumptions of fixed known odds and independent outcomes do not hold in markets. Applied naively to daily equity returns it asks for leverage well past what any account can carry, as the first panel above shows.
What happens if you bet more than the Kelly fraction?
The long-run growth rate falls. At roughly twice the Kelly fraction it reaches about zero, and beyond that a bet with a real edge shrinks capital over time while its drawdowns keep deepening.
Is the Kelly criterion the same as risking 1% or 2% per trade?
No. A fixed-percentage rule ignores the odds entirely and applies the same number to every setup. Kelly scales the stake with the measured edge, which makes it more responsive when the edge is known and more fragile when the edge is guessed.
Every figure above comes from a stored query you can open, edit, and re-run. Swap the tickers, the window, or the bet-size grid and measure the tradeoff yourself on the Strasmore terminal.