Text Generation using GPT Models
Calling model.eval() switches the model into evaluation mode, which disables dropout because the run is not training the model.
Watching a GPT Model Continue a Sentence
This article follows one short text generation run from start to finish. Rather than starting with definitions, we begin with the result: a GPT model is given a piece of text and asked to continue it. The output of that run is a list of integers, not readable words. The goal is to understand what the model returned and then work backward through each part of the run to see how that result was produced.
Think of the run as a pipeline with three visible stages: prepare the model, call the generation function, and read the output. Each stage can go wrong in a different way, and the output length gives you a way to tell which stage is responsible when something looks off. We will return to that idea later in the article.
Why the Model Enters Evaluation Mode
Before generating anything, the model is placed into evaluation mode by calling model.eval(). The source describes this call as the switch that disables random components such as dropout. In other words, calling model.eval() changes how the model behaves for the rest of the run.
Evaluation mode is the state a model is placed in with model.eval() when it is being used to produce output rather than to learn. In this state, random components such as dropout are disabled.
Dropout is a training-time mechanism. During learning, it introduces randomness so the model does not depend too heavily on any single internal component. When the model is only being run to produce output, that randomness is not wanted, because the same input should not give a different continuation simply because a random component was switched on. Evaluation mode turns that randomness off.
| Question | Training mode | Evaluation mode (model.eval()) |
|---|---|---|
| Purpose of the run | The model is learning from data | The model is only producing output |
| Dropout | Used, because it is a training-time mechanism | Disabled, so no random dropping happens |
| Typical use in this run | Not the state used for generation | The state used before calling the generation function |
What changes when a model is switched into evaluation mode
Arguments to generate_text_simple
The generation step is a single call to generate_text_simple. It takes four pieces of information: the model to use, an encoded input tensor named idx, a limit on how many new tokens to add through max_new_tokens, and a context size taken from the model configuration as its context length. Each argument answers a separate question. Which model should produce the continuation? What are the starting tokens? How far should the model continue? How much of the preceding text may the model look at?
model.eval()runs first, so dropout is disabled before any output is produced- idx carries the starting tokens as token IDs, not as raw text
max_new_tokens=6 caps how many new tokens the function addscontext_sizetells the function how much preceding text it may consider
The function returns output token IDs. It does not return readable words. To read the result as text, the IDs must be mapped back through the tokenizer's vocabulary. Keep this distinction in mind: the printed output is a sequence of integers, and seeing integers is the expected result at this stage of the run.
Tracing the Token Sequence Step by Step
Generation works by growing the token sequence. The input begins with its own tokens, and on each iteration one new token is added to the end. The number of iterations is capped by max_new_tokens. The diagram below traces the length of the sequence through the run, using the values from the source: an input of 4 tokens and a limit of 6 new tokens.
Each iteration adds exactly one token, so the sequence length rises by one at every step. After six iterations, the sequence has grown from 4 tokens to 10. The earlier tokens are never removed; the model's continuation is simply appended to what was already there. This is why the final output contains the original input followed by the newly generated tokens.
Using Output Length as a Checkpoint
The reported output length of 10 equals the 4 input tokens plus the 6 newly generated tokens. Because this relationship is predictable, the output length is a useful checkpoint. If you know the input length and max_new_tokens, you know what length the output should have. When the printed length differs from that expectation, something upstream has changed.
- 1Count the tokens in the encoded input: here, 4.
- 2Read the limit set by
max_new_tokens: here, 6. - 3Add them: 4 + 6 = 10, which is the length the output should have.
The useful question is not only what was printed, but at which step the printed value stopped matching what the code should produce. Because the length grows by one per iteration, you can compare the observed length against the expected length at each checkpoint. The first point of divergence narrows down where the problem entered the run.
Mistakes Beginners Make with the Output
Common mistake Expecting readable words from generate_text_simple
What it looks likePrinting the result and expecting a sentence to appear.
Why it failsThe function returns output token IDs, which are integers.
Do this insteadExpect integers at this stage, and map them back through the vocabulary to read them as text.
Common mistake Skipping model.eval() because the code runs anyway
Why it failsThe model still runs, but dropout remains active, so the run includes training-time randomness that was not intended.
Do this insteadCall model.eval() before generating text.Common mistake Reading a wrong output length as a random glitch
What it looks likeThe output has 9 tokens when 10 were expected, and the cause is left unexamined.
Why it failsThe length has a predictable relationship to the input length and
max_new_tokens, so a mismatch is a signal.Do this insteadCompare the observed length with the expected length, find the first step where they diverge, and inspect what changed upstream.
Predicting the Output Length
What do you think happens?
The encoded input has 4 tokens and max_new_tokens is set to 6. How many tokens will the output contain?
Reveal answer
10 tokens
The output length equals the 4 input tokens plus the 6 newly generated tokens, giving 10.
Suppose a run is set up with an encoded input of 4 tokens and max_new_tokens of 6, but the printed output contains only 9 tokens. Using the checkpoint idea, at which point would you start your investigation, and what would you check first?
Hints
- Compute the expected length first.
- Think about whether the mismatch appeared before or after the function was called.
- Consider what the input to the function looked like.
Key Takeaways
- Calling
model.eval()switches the model into evaluation mode, which disables dropout because the run is only producing output rather than training. generate_text_simpletakes a model, an encoded input tensor idx, amax_new_tokenslimit, and a context size, and returns output token IDs rather than readable text.- The output length equals the input length plus
max_new_tokens, so with 4 input tokens and a limit of 6, the expected output length is 10. - When the observed output length diverges from the expected length, the first step where they differ shows where the problem entered the run.