LLMsLoading progress…

Next-token targets

Build a smoothed bigram model and connect next-token probabilities to log loss and perplexity.

What the model is asked to guess

A language model assigns a probability to the next token given what came before. Training data needs no labels: the text itself supplies them. Every token is the target for the token (or tokens) just before it, so the targets are the same sequence shifted left by one.

#input (current token)target (next token)
1the→cat
2cat→sat
3sat→on
4on→the
5the→mat
6 tokens → 5 pairs inputs : the cat sat on the targets: cat sat on the mat (the same list shifted left by one)
Type any text. Each adjacent pair is one training example; start and end markers add one pair at each end.

Predict first. For tokens a, b, c, what are the adjacent training pairs?

inputs, targets = tokens[:-1], tokens[1:]     # shifted by one
Chapter context

A causal language model predicts the next token from the allowed prefix. A bigram model is a transparent starting point: it uses only the immediately preceding token, making counts, uncertainty and sampling easy to inspect.

Chapter reference: math, worked example & code

This section belongs to the whole chapter, so it is the same on every lesson in it and may cover a different lesson's topic. The code for the experiment you just ran is inside the experiment itself.

Math and notation

P(y∣x)=C(x,y)+α∑jC(x,j)+αV,NLL⁡=−1N∑tlog⁡P(xt+1∣xt).P(y\mid x)=\frac{C(x,y)+\alpha}{\sum_j C(x,j)+\alpha V},\quad \operatorname{NLL}=-\frac1N\sum_t\log P(x_{t+1}\mid x_t).

V is the output vocabulary size and alpha is a nonnegative smoothing amount. Perplexity is exp(NLL) for natural-log loss.

Worked example

For ababa, a→b occurs twice and b→a occurs twice. With vocabulary {a,b} and alpha=1, P(b|a)=(2+1)/(2+2)=0.75. An alternating transition then incurs −ln(0.75)≈0.287682 nats, whose perplexity is 4/3.

Reference code

The following example uses the Python standard library and does not call a remote service.

from math import log,exp,isclose
seq='ababa'
count=sum(a=='a' and b=='b' for a,b in zip(seq,seq[1:]))
assert count == 2
prob=(count+1)/(2+2)
assert prob == .75
assert isclose(-log(prob),.2876820724517809)
assert isclose(exp(-log(prob)),4/3)

Python examples are provided for study and local execution; this page does not execute Python.

Common mistakes

Predicting the input token itself can create target leakage. Bigram counts depend on token boundaries. Perplexities across incompatible tokenizers are not directly comparable.