0Pricing
AI Prompt Engineering · 课时

Top-k 采样

将选择范围限制为概率最高的 k 个词元,以及这种做法对输出多样性的影响。

Top-k 采样 是 CoddyKit 上的免费 AI Prompt Engineering 课时。 这是第 3 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 AI Prompt Engineering 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 AI Prompt Engineering 课程共包含 4 节课。

什么是 Top-k 采样?

Top-k 采样会将模型限制在每一步概率最高的 k 个词元中进行采样。Top-k 之外的所有词元都会被赋予零概率,无法被选中。

k=1 是贪心解码(只有概率最高的单个词元)。k=50 是典型的创意范围。k=词汇表大小等同于不受限制的采样。

Top-k 算法

该算法比 Top-p 更简单:

  1. 计算完整词汇表上的 softmax 概率
  2. 按概率降序排列词元
  3. 只保留前 k 个词元;将其他所有词元的概率设为 0
  4. 重新归一化 Top-k 的概率,使总和为 1
  5. 从重新归一化后的分布中采样
import numpy as np

def softmax(logits, temperature=1.0):
    scaled = logits / temperature
    e = np.exp(scaled - np.max(scaled))
    return e / e.sum()

def top_k_sample(logits, k=50, temperature=1.0):
    probs = softmax(logits, temperature)

    # Find top-k indices
    top_k_indices = np.argsort(probs)[::-1][:k]
    top_k_probs = probs[top_k_indices]

    # Renormalize
    top_k_probs = top_k_probs / top_k_probs.sum()

    # Sample
    chosen = np.random.choice(top_k_indices, p=top_k_probs)
    return chosen

# With a 10-token vocabulary:
logits = np.random.randn(10)
print('Chosen token:', top_k_sample(logits, k=3))

k=1:贪心解码

当 k=1 时,候选集中只有概率最高的单个词元。从大小为 1 的集合中采样是确定性的——模型始终选择该词元。这与贪心解码(温度=0)完全相同。

logits = np.array([3.0, 2.0, 1.0, 0.5, -1.0])

# k=1: greedy
top_1 = top_k_sample(logits, k=1)
print(f'k=1 always picks: {np.argmax(logits)}')  # index 0, the highest logit
print(f'top_k_sample result: {top_1}')  # always 0

# Multiple runs
for _ in range(5):
    print(top_k_sample(logits, k=1), end=' ')
# Output: 0 0 0 0 0 — perfectly deterministic

典型创意范围:k=50

k=50 是创意文本生成中常见的默认值。它允许模型在每一步从 50 个词元中进行探索,同时防止模型选择其置信度极低的词元。

当词汇表包含 50,000 个词元时,k=50 意味着模型在每一步只考虑排名前 0.1% 的词元。这是一个相当大的限制——词汇表中的大多数词元都会被排除。

import openai
client = openai.OpenAI(api_key='sk-...')

# Note: OpenAI API does not expose top_k directly in chat completions.
# Top-k is primarily a parameter in Hugging Face Transformers and Anthropic's API.

# Hugging Face example:
from transformers import pipeline
generator = pipeline('text-generation', model='gpt2')
output = generator(
    'Once upon a time',
    max_new_tokens=100,
    do_sample=True,
    top_k=50,
    temperature=1.0
)
print(output[0]['generated_text'])

Anthropic 的 Claude API 中的 Top-k

Anthropic 的 Claude API 将 top_k 作为直接参数公开。这使得尝试固定词汇表截断对 Claude 输出的影响变得十分容易。

import anthropic
claude = anthropic.Anthropic(api_key='sk-ant-...')

# top_k limits the number of tokens considered
message = claude.messages.create(
    model='claude-opus-4-5',
    max_tokens=256,
    temperature=1.0,
    top_k=50,  # sample from top 50 most probable tokens
    messages=[{
        'role': 'user',
        'content': 'Write a short poem about debugging code.'
    }]
)
print(message.content[0].text)

固定 k 的问题

Top-k 的根本限制是:无论模型在该步骤的置信度如何,k 都是固定的。

当模型非常确定时(某个词元的概率为 95%),k=50 仍会包含 49 个基本无关的词元。当模型非常不确定时(50 个词元的概率各约为 2%),k=50 可能确实很合适。

问题在于:根据上下文不同,k=50 可能同时过于严格或过于宽松。Top-p 通过动态调整核大小解决了这一问题。

# Illustrating the fixed-k problem
logits_confident = np.array([5.0] + [0.1] * 9)  # model is very sure
logits_uncertain = np.array([1.0] * 10)           # model has no idea

probs_conf = softmax(logits_confident)
probs_unc = softmax(logits_uncertain)

print('Confident — top 3 tokens cover:', np.sort(probs_conf)[::-1][:3].sum().round(3))
# ~0.998 — k=50 is extremely wasteful, includes near-zero probability tokens

print('Uncertain — top 3 tokens cover:', np.sort(probs_unc)[::-1][:3].sum().round(3))
# ~0.30 — k=50 may actually be needed to cover a reasonable nucleus

分布尾部的 Top-k

Top-k 和 Top-p 在分布尾部的差异最为明显:

  • 使用 top-k=50 时,第 50 个词元的概率可能只有 0.001%(极不可能,但仍在候选集中)
  • 使用 top-p=0.9 时,任何位于 90% 核之外的词元都会被排除,包括原本会进入 Top-k 的词元

Top-p 对尾部行为的处理更合理:它根据概率而不是排名位置来排除低概率词元。

# Tail behavior comparison
import numpy as np

# Highly skewed distribution (one dominant token)
skewed_logits = np.array([4.0, 2.0, 1.5, 1.0, 0.5,
                           0.1, 0.0, -0.1, -0.5, -1.0])
probs = softmax(skewed_logits)

print('Probability of tokens 6-9 (tail):')
for i in range(6, 10):
    print(f'  Token {i}: {probs[i]:.4%}')
# These tokens are very unlikely but are included in top-k=10
# Top-p=0.9 would exclude them entirely

结合 Top-k 与 Top-p

一些实现会同时应用 Top-k 和 Top-p:先截断到 Top-k,再在该集合中应用 Top-p 核采样。这样既能通过 Top-k 对词汇表大小设置硬上限,又能通过 Top-p 应用基于概率的筛选。

def top_k_top_p_sample(logits, k=50, p=0.9, temperature=1.0):
    probs = softmax(logits, temperature)

    # First apply top-k
    top_k_indices = np.argsort(probs)[::-1][:k]
    top_k_probs = probs[top_k_indices]

    # Then apply top-p within top-k
    sorted_k = np.sort(top_k_probs)[::-1]
    cumulative = np.cumsum(sorted_k)
    nucleus_size = np.searchsorted(cumulative, p) + 1

    final_indices = top_k_indices[:nucleus_size]
    final_probs = top_k_probs[:nucleus_size]
    final_probs = final_probs / final_probs.sum()

    return np.random.choice(final_indices, p=final_probs)

何时优先使用 Top-k 而不是 Top-p

尽管 Top-p 在理论上具有优势,但在某些场景中更适合使用 Top-k:

  • 词汇表受限的任务:当模型只能从固定集合中输出时(例如多项选择 A/B/C/D),较小的 Top-k(4)可以直接强制实现这一限制
  • 可复现性:Top-k 的行为更容易推断——“始终恰好考虑 50 个词元”
  • 经过硬件优化的实现:某些推理引擎实现 Top-k 的效率高于 Top-p
# Constrained output with top-k=4
# For a multiple choice task (A, B, C, D)
# If A/B/C/D tokens have indices 32, 33, 34, 35
# top-k=4 with those as the top-4 logits forces selection from those 4 only

multiple_choice_prompt = (
    'Answer with only A, B, C, or D.\n'
    'What is the capital of France?\n'
    'A) Berlin\n'
    'B) Paris\n'
    'C) Rome\n'
    'D) Madrid\n'
    'Answer:'
)

# With temperature=0, top_k=1: always picks the highest logit token

Top-k 实用指南

何时使用 Top-k,以及如何选择其值:

  • k=1:贪心 / 事实型任务
  • k=5–20:侧重集中的创意任务,变化最小
  • k=40–100:大多数语言模型中的标准创意范围
  • k=500+:非常开放的探索(很少需要;请改用 Top-p)

在大多数现代 LLM API 中,Top-p 是首选参数。当您需要对词汇表设置硬上限,或 API 提供 Top-k 但不提供 Top-p 时,请使用 Top-k。

TOP_K_GUIDELINES = {
    'factual_qa': 1,           # greedy
    'code_generation': 10,     # near-greedy, correct syntax
    'summarization': 20,       # slightly varied but focused
    'chat': 50,                # natural variation
    'creative_writing': 100,   # wider vocabulary exploration
    'poetry': 200,             # unusual word choices encouraged
}

def call_with_top_k(task, prompt, model='claude-opus-4-5'):
    k = TOP_K_GUIDELINES.get(task, 50)
    claude = anthropic.Anthropic(api_key='sk-ant-...')
    return claude.messages.create(
        model=model,
        max_tokens=512,
        top_k=k,
        messages=[{'role': 'user', 'content': prompt}]
    )

Top-k 与温度结合

Top-k 和温度会按顺序应用:先由温度重新塑造对数几率分布,再由 Top-k 将其截断为概率最高的 k 个词元。在 Hugging Face Transformers 管道中,同时使用二者很常见。

典型组合:温度=0.9(适度多样性)+ Top-k=50(严格限制词汇表)。这样既能避免单独使用高温度时分布过于平坦,也能避免从尾部采样的问题。

from transformers import pipeline

generator = pipeline('text-generation', model='gpt2')

# Combined top-k + temperature
output = generator(
    'The future of AI is',
    max_new_tokens=80,
    do_sample=True,
    top_k=50,
    temperature=0.9
)
print(output[0]['generated_text'])

# Compare: top-k=1 (greedy)
greedy_output = generator(
    'The future of AI is',
    max_new_tokens=80,
    do_sample=False  # greedy, equivalent to top_k=1
)
print(greedy_output[0]['generated_text'])

知识检查

在 Top-k 采样中,如果设置 k=1,模型会表现出哪种行为?

回顾:Top-k 采样

Top-k 采样会在采样前将词汇表截断为概率最高的 k 个词元:

  • k=1:贪心解码——具有确定性,总是选择概率最高的词元
  • k=50:典型的创作范围——在多样性和连贯性之间取得平衡
  • 主要限制:无论模型的置信度如何,k 都是固定的——可能过于宽松,也可能过于严格
  • 与 top-p 相比:top-p 的动态核心集合会适应置信度,而 top-k 不会

当您需要严格限制词汇表时,请使用 Top-k。对于大多数生产应用,优先选择 top-p。下一课:为您的具体使用场景选择参数。

常见问题解答

「Top-k 采样」课时是免费的吗?

是的 — 「Top-k 采样」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 AI Prompt Engineering 课程的其余内容,请升级到 CoddyKit PRO。 AI Prompt Engineering 课程共包含 4 节课。

「Top-k 采样」这节课中我会学到什么?

将选择范围限制为概率最高的 k 个词元,以及这种做法对输出多样性的影响。 你通过在浏览器中直接运行的动手代码来练习 AI Prompt Engineering,全天候 AI 导师会在你学习这节课的过程中回答你的问题。

学习 AI Prompt Engineering 需要有经验吗?

无需任何先前经验。CoddyKit 上的 AI Prompt Engineering 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 3 节课,共 4 节。

「Top-k 采样」课时需要多长时间?

大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。

我能在这节 AI Prompt Engineering 课中编写并运行代码吗?

能。每节 AI Prompt Engineering 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。

此课程中的所有课时

  1. LLM 中的温度是什么?
  2. Top-p 核采样
  3. Top-k 采样
  4. 为您的使用场景选择参数
← 返回 AI Prompt Engineering