{"course":{"slug":"how-llms-work","title":"How a Language Model Actually Works","url":"https://addaly.com/learn/how-llms-work","level":"intermediate","track":"start"},"lesson":{"slug":"from-final-vector-to-logits","title":"From the final vector to a score for every word","url":"https://addaly.com/learn/how-llms-work/from-final-vector-to-logits","position":17,"of":78,"minutes":8,"answer":"The last step compares the final vector against every vocabulary entry, and doing that comparison at intermediate layers lets you watch an answer form.","keyIdea":"The last step compares the final vector against every vocabulary entry, and doing that comparison at intermediate layers lets you watch an answer form."},"body":{"format":"markdown","text":"## The last operation in the stack\n\nAfter the final block, the vector at the last position is one list of, say, 4,096 numbers. It has to become a score for each of 128,256 possible next tokens. That happens with a single matrix multiplication against the unembedding matrix (one row per vocabulary entry) producing one number per entry.\n\n```python\nlogits = final_vector @ W_unembed.T      # (4096,) @ (4096, 128256) -> (128256,)\n```\n\nEach logit is a dot product: how well does the final vector align with this token's direction? Highest alignment, highest score.\n\nTwo consequences worth noticing. This one operation costs about 525 million multiply-adds in an 8B model, comparable to a whole layer, which is why large vocabularies are not free. And because it is a linear comparison against fixed directions, the geometry of the embedding space directly determines which tokens can be strongly preferred at all.\n\n## Tied embeddings\n\nMany models use the *same* matrix for input embedding and output unembedding, transposed. The argument is that a token's input representation and the direction that predicts it should be related, and the saving is substantial: 525 million parameters in the model we counted.\n\nTying helps most in small models, where the vocabulary is a large share of the total. Larger models often untie, on the finding that the two roles benefit from being learned separately. Either way, `config.json` tells you: look for `tie_word_embeddings`.\n\n## Logits are not probabilities\n\nThe output at this stage is unnormalised. Logits are real numbers, positive or negative, with no ceiling. Softmax converts them to probabilities, and the *differences* between logits are what matter: adding a constant to every logit changes nothing after softmax.\n\nThis is worth internalising because logits are what temperature acts on, as module three covers. Temperature divides the logits before the softmax, which is why it reshapes the distribution rather than picking differently from a fixed one.\n\n## The logit lens\n\nNow the interesting part. Nothing stops you applying the final unembedding to an *intermediate* layer's vector, since the residual stream keeps the same width all the way through. Do it at every layer and you get a running readout of what the model would say if it stopped there.\n\n```python\nfor layer, h in enumerate(hidden_states):     # h: the residual stream after layer `layer`\n    logits = norm_final(h[0, -1]) @ W_unembed.T\n    top = logits.argmax().item()\n    print(layer, tokenizer.decode([top]))\n```\n\nOn a factual prompt you typically see noise in the lower layers, a plausible category emerging in the middle, and the specific answer sharpening in the last quarter. It is a striking thing to watch, and it runs on a small model on a free Colab or Kaggle notebook in ten minutes with Hugging Face `transformers` and `output_hidden_states=True`.\n\n## What the logit lens does not prove\n\nRead it carefully. The technique assumes intermediate vectors are meaningfully comparable to the final unembedding directions, an assumption that holds better in some models than others, and fails outright in a few. Refinements such as the \"tuned lens\" fit a small transformation per layer to correct for this, and they change the picture at some layers, which tells you the raw version was partly artefact.\n\nMore generally: seeing an answer appear at layer 22 does not mean layer 22 \"decided\" it. The residual stream is a sum, and later layers routinely suppress or redirect what earlier ones wrote. The lens shows a projection of a running total, not a sequence of decisions.\n\n## Why this is practically useful\n\nThree uses that survive the caveats.\n\n**Debugging your own fine-tune.** If a fine-tuned model gives the right answer at layer 20 and the wrong one at layer 32, the damage is in the top layers, and that is a different problem from the model never knowing the answer.\n\n**Understanding confidence.** The gap between the top two logits at the final layer is the raw material of every confidence measure you will use in module six.\n\n**Deflating mystique.** A model does not retrieve an answer and then phrase it. It accumulates evidence across a stack of identical blocks until one direction wins, and you can watch that happen."},"check":{"question":"What does the logit lens actually show when it reveals the correct answer appearing at layer 22 of 32?","options":[{"text":"That layer 22 is where the model retrieves the fact from its feed-forward weights.","correct":false,"tempting":"Facts do live largely in the feed-forward layers, so pointing at a specific layer as the retrieval site feels well-grounded."},{"text":"That layers 23 to 32 are redundant for this prompt and could be skipped.","correct":false,"tempting":"Layer-skipping and early exit are real techniques, which makes this a natural engineering conclusion to draw."},{"text":"That the running total in the residual stream at layer 22, projected onto the output directions, already aligns most with that token, while later layers can still suppress or redirect it.","correct":true},{"text":"That the model has committed to the answer and the remaining layers only adjust phrasing.","correct":false,"tempting":"A \"decide then phrase\" pipeline is an intuitive picture of generation and matches how people write."}]},"prev":{"slug":"normalisation-and-stability","title":"Normalisation, and why training is fragile","url":"https://addaly.com/learn/how-llms-work/normalisation-and-stability"},"next":{"slug":"mixture-of-experts","title":"Mixture of experts: big model, small bill","url":"https://addaly.com/learn/how-llms-work/mixture-of-experts"},"authorship":"Founder and series editor: Dr Mustafa Mun. Written by AI models to a written standard. Exam keys checked blind by a second model: 3,665 of 3,666 agreed. Academic review invited.","review":{"status":"Draft, open for academic review"},"cite":"Addaly (2026) 'From the final vector to a score for every word', in How a Language Model Actually Works. Edited by M. Mun. Addaly. Available at: https://addaly.com/learn/how-llms-work/from-final-vector-to-logits (Accessed: 13 October 2026).","licence":{"name":"CC BY-NC-SA 4.0","url":"https://creativecommons.org/licenses/by-nc-sa/4.0/"},"reader":{"schema":1,"title":"From the final vector to a score for every word","courseTitle":"How a Language Model Actually Works","module":{"index":2,"slug":"inside-the-block","title":"Inside the block"},"answer":null,"keyIdea":"The last step compares the final vector against every vocabulary entry, and doing that comparison at intermediate layers lets you watch an answer form.","hero":{"kind":"plate","image":null,"alt":null,"caption":null},"blocks":[{"t":"h2","id":"the-last-operation-in-the-stack","runs":[{"text":"The last operation in the stack"}]},{"t":"p","runs":[{"text":"After the final block, the vector at the last position is one list of, say, 4,096 numbers. It has to become a score for each of 128,256 possible next tokens. That happens with a single matrix multiplication against the unembedding matrix (one row per vocabulary entry) producing one number per entry."}]},{"t":"code","lang":"python","label":"Python","text":"logits = final_vector @ W_unembed.T      # (4096,) @ (4096, 128256) -> (128256,)"},{"t":"p","runs":[{"text":"Each logit is a dot product: how well does the final vector align with this token’s direction? Highest alignment, highest score."}]},{"t":"p","runs":[{"text":"Two consequences worth noticing. This one operation costs about 525 million multiply-adds in an 8B model, comparable to a whole layer, which is why large vocabularies are not free. And because it is a linear comparison against fixed directions, the geometry of the embedding space directly determines which tokens can be strongly preferred at all."}]},{"t":"h2","id":"tied-embeddings","runs":[{"text":"Tied embeddings"}]},{"t":"p","runs":[{"text":"Many models use the "},{"text":"same","i":true},{"text":" matrix for input embedding and output unembedding, transposed. The argument is that a token’s input representation and the direction that predicts it should be related, and the saving is substantial: 525 million parameters in the model we counted."}]},{"t":"p","runs":[{"text":"Tying helps most in small models, where the vocabulary is a large share of the total. Larger models often untie, on the finding that the two roles benefit from being learned separately. Either way, "},{"text":"config.json","code":true},{"text":" tells you: look for "},{"text":"tie_word_embeddings","code":true},{"text":"."}]},{"t":"h2","id":"logits-are-not-probabilities","runs":[{"text":"Logits are not probabilities"}]},{"t":"p","runs":[{"text":"The output at this stage is unnormalised. Logits are real numbers, positive or negative, with no ceiling. Softmax converts them to probabilities, and the "},{"text":"differences","i":true},{"text":" between logits are what matter: adding a constant to every logit changes nothing after softmax."}]},{"t":"p","runs":[{"text":"This is worth internalising because logits are what temperature acts on, as module three covers. Temperature divides the logits before the softmax, which is why it reshapes the distribution rather than picking differently from a fixed one."}]},{"t":"h2","id":"the-logit-lens","runs":[{"text":"The logit lens"}]},{"t":"p","runs":[{"text":"Now the interesting part. Nothing stops you applying the final unembedding to an "},{"text":"intermediate","i":true},{"text":" layer’s vector, since the residual stream keeps the same width all the way through. Do it at every layer and you get a running readout of what the model would say if it stopped there."}]},{"t":"code","lang":"python","label":"Python","text":"for layer, h in enumerate(hidden_states):     # h: the residual stream after layer `layer`\n    logits = norm_final(h[0, -1]) @ W_unembed.T\n    top = logits.argmax().item()\n    print(layer, tokenizer.decode([top]))"},{"t":"p","runs":[{"text":"On a factual prompt you typically see noise in the lower layers, a plausible category emerging in the middle, and the specific answer sharpening in the last quarter. It is a striking thing to watch, and it runs on a small model on a free Colab or Kaggle notebook in ten minutes with Hugging Face "},{"text":"transformers","code":true},{"text":" and "},{"text":"output_hidden_states=True","code":true},{"text":"."}]},{"t":"h2","id":"what-the-logit-lens-does-not-prove","runs":[{"text":"What the logit lens does not prove"}]},{"t":"p","runs":[{"text":"Read it carefully. The technique assumes intermediate vectors are meaningfully comparable to the final unembedding directions, an assumption that holds better in some models than others, and fails outright in a few. Refinements such as the “tuned lens” fit a small transformation per layer to correct for this, and they change the picture at some layers, which tells you the raw version was partly artefact."}]},{"t":"p","runs":[{"text":"More generally: seeing an answer appear at layer 22 does not mean layer 22 “decided” it. The residual stream is a sum, and later layers routinely suppress or redirect what earlier ones wrote. The lens shows a projection of a running total, not a sequence of decisions."}]},{"t":"h2","id":"why-this-is-practically-useful","runs":[{"text":"Why this is practically useful"}]},{"t":"p","runs":[{"text":"Three uses that survive the caveats."}]},{"t":"p","runs":[{"text":"Debugging your own fine-tune.","b":true},{"text":" If a fine-tuned model gives the right answer at layer 20 and the wrong one at layer 32, the damage is in the top layers, and that is a different problem from the model never knowing the answer."}]},{"t":"p","runs":[{"text":"Understanding confidence.","b":true},{"text":" The gap between the top two logits at the final layer is the raw material of every confidence measure you will use in module six."}]},{"t":"p","runs":[{"text":"Deflating mystique.","b":true},{"text":" A model does not retrieve an answer and then phrase it. It accumulates evidence across a stack of identical blocks until one direction wins, and you can watch that happen."}]}],"check":{"question":[{"text":"What does the logit lens actually show when it reveals the correct answer appearing at layer 22 of 32?"}],"options":[{"text":[{"text":"That layer 22 is where the model retrieves the fact from its feed-forward weights."}],"correct":false,"tempting":[{"text":"Facts do live largely in the feed-forward layers, so pointing at a specific layer as the retrieval site feels well-grounded."}]},{"text":[{"text":"That layers 23 to 32 are redundant for this prompt and could be skipped."}],"correct":false,"tempting":[{"text":"Layer-skipping and early exit are real techniques, which makes this a natural engineering conclusion to draw."}]},{"text":[{"text":"That the running total in the residual stream at layer 22, projected onto the output directions, already aligns most with that token, while later layers can still suppress or redirect it."}],"correct":true,"tempting":null},{"text":[{"text":"That the model has committed to the answer and the remaining layers only adjust phrasing."}],"correct":false,"tempting":[{"text":"A “decide then phrase” pipeline is an intuitive picture of generation and matches how people write."}]}],"order":[0,3,2,1],"why":null},"prev":{"slug":"normalisation-and-stability","title":"Normalisation, and why training is fragile","minutes":8},"next":{"slug":"mixture-of-experts","title":"Mixture of experts: big model, small bill","minutes":9}}}