DEV Community

Cover image for The maths behind an options yield matrix (and why raw premium misleads you)
Options Matrix Pro
Options Matrix Pro

Posted on

The maths behind an options yield matrix (and why raw premium misleads you)

I build Options Matrix Pro, a web app for researching options trades. The feature people ask about most is the yield matrix: a heatmap with expiries down the side, strikes across the top, and one number in every cell. This post explains what goes into that number, using a real NVIDIA snapshot, and the small amount of code it takes.

Disclosure: I'm the founder of Options Matrix Pro. Nothing here is a trade recommendation. Options can lose more than the premium you collect, and selling puts means you may have to buy the shares.

The problem: premiums are not comparable

Say you want to sell a cash-secured put on NVDA. Before the US open on 3 November 2026 the stock was quoted at about $205. The chain showed, among many others:

Strike Expiry Days to expiry Mid premium
$195 6 Nov 3 $1.98
$200 27 Nov 24 $9.40

$9.40 looks far better than $1.98. It isn't that simple. The $200 put ties up more cash, for eight times as long, at a strike much closer to the current price. To compare contracts you need to divide by the capital at risk and by time.

Three numbers per contract

A cash-secured put on 100 shares reserves strike × 100 in cash. From there:

// One short put, one contract (100 shares).
function cspMetrics({ strike, premium, dte, spot }) {
  const collateral = strike * 100;
  const credit = premium * 100;
  const premiumYield = credit / collateral;          // return on cash reserved, for the whole trade
  const monthlyYield = premiumYield * (30 / dte);    // same return scaled to a 30-day month
  const breakeven = strike - premium;                // price where the trade starts losing at expiry
  const cushion = (spot - breakeven) / spot;         // how far the stock can fall before that
  return { collateral, credit, premiumYield, monthlyYield, breakeven, cushion };
}

cspMetrics({ strike: 195, premium: 1.98, dte: 3, spot: 205.14 });
// credit $198, premiumYield 1.02%, monthlyYield 10.2%, breakeven $193.02, cushion 5.9%

cspMetrics({ strike: 200, premium: 9.40, dte: 24, spot: 205.14 });
// credit $940, premiumYield 4.70%, monthlyYield 5.9%, breakeven $190.60, cushion 7.1%
Enter fullscreen mode Exit fullscreen mode

Now the comparison flips. The 3-day put earns more per month, but the 24-day put has a bigger cushion before it loses money. Neither is "better". They are different bets, and the point of the matrix is to show those trade-offs side by side instead of one contract at a time.

Here is the same data in the app's details table. The numbers above are exactly what it shows:

NVDA cash-secured put details table in Options Matrix Pro, sorted by monthly premium yield

Turning it into a heatmap

The matrix is just those metrics pivoted: rows are expiries, columns are strikes, and the cell value is whichever metric you pick (monthly yield, POP, delta, breakeven and so on). Cells that fail your filters, such as a minimum probability of profit or a delta range, are left blank, so the blanks carry information too.

function buildMatrix(contracts, metric, passes) {
  const expiries = [...new Set(contracts.map(c => c.expiry))].sort();
  const strikes = [...new Set(contracts.map(c => c.strike))].sort((a, b) => a - b);
  const cell = new Map(contracts.filter(passes).map(c => [`${c.expiry}|${c.strike}`, c[metric]]));
  return expiries.map(e => strikes.map(s => cell.get(`${e}|${s}`) ?? null));
}
Enter fullscreen mode Exit fullscreen mode

Colour is scaled per metric so the eye goes to the highest values first. Two extra layers make it far more useful than a coloured spreadsheet:

  • Expected move. The dashed marker in each row is where the market's expected move puts the stock at that expiry (derived from the at-the-money straddle). Strikes outside it have a cushion the options market itself thinks is wide.
  • Event flags. The 20 November row carries an ER badge: NVIDIA reports earnings before that expiry, so its premiums are inflated for a reason.

NVDA monthly premium yield heatmap with expected-move markers and an earnings flag

The cell is not the decision

Click any cell and the app opens that exact contract in a payoff visualizer, so you can see the shape of the risk rather than one summary number. For the $200 put: $940 maximum profit, a $190.60 breakeven, and a loss that keeps growing below it.

The NVDA 200 put modelled in the Options Matrix Pro strategy visualizer

A few limits worth stating plainly, because a yield matrix makes it easy to forget them:

  1. Monthly yield exaggerates short trades. Scaling a 3-day return to 30 days assumes you can repeat it ten times at the same price, which you can't.
  2. Mid prices are not fills. Wide bid/ask spreads on illiquid strikes can turn a good-looking cell into a poor trade.
  3. Probability of profit is model output. It comes from implied volatility, not a forecast.
  4. Assignment is the point, not a side effect. If NVDA closes below the strike you buy 100 shares, and the loss below breakeven is real.

Try it

You can build the same view with any options chain API and the snippets above. If you'd rather not, the Options Matrix does this for every strike and expiry with live ThetaData quotes, and the free cash-secured put calculator runs the single-contract maths with no account. Coming from OptionStrat? There's an honest feature comparison.

I'd love feedback from anyone who has built something similar, especially on how you handle expiries with very few days left.

Top comments (0)