第01章 · LLM 基础 —— 与模型对话的第一步

分享

目标:理解 LLM API 的核心概念,能用 Python/TypeScript 发出第一个请求并读懂返回值。 这是整个教程的地基——后续 16 章的 Agent 循环、工具调用、记忆系统全都建立在此之上。

TL;DR

30 秒速读:LLM API 就是一个 HTTP 接口,你发 messages 数组,它返回补全文本,每次调用完全独立,模型不会记住任何历史。

如果只记一件事:messages 数组里的 role(system/user/assistant)决定了"谁在说话",system prompt 是你控制模型行为的最强杠杆。


1. LLM API 是什么?

大语言模型(LLM)本身是一个运行在服务器上的数学函数——你给它一段文字(prompt),它返回一段补全(completion)。 我们通过 HTTP API 调用它,就像调用任何 REST 接口一样。

你的代码  →  HTTP POST  →  LLM 服务器  →  HTTP Response  →  拿到回答

好消息:几乎所有主流 LLM 提供商(OpenAI、DeepSeek、Qwen、Ollama)都兼容 同一套请求格式—— OpenAI Chat Completions API。学一次,到处能用。

请求的核心结构

{
  "model": "gpt-4o-mini",
  "messages": [
    {"role": "system", "content": "你是一个任务助手"},
    {"role": "user",   "content": "帮我总结一下今天的待办"}
  ]
}

三个关键字段: - model:用哪个模型(不同模型能力/价格不同) - messages:对话历史,是一个有序数组 - role:每条消息的"说话人"——这是理解 LLM 的关键


2. 角色模型(Roles)

Chat Completions API 有三个角色,它们共同构成一次"对话":

角色 谁说的 作用 举例
system 开发者(你) 定义 AI 的"人格"和行为边界 "你是一个任务助手,只回答与待办相关的问题"
user 终端用户 发送实际问题或指令 "帮我列一下今天的待办"
assistant AI 模型 模型的回答 "好的,以下是你的待办清单:1. …"

关键理解system 消息不是"系统自动的",而是你写的。 它相当于给 AI 演员一份"角色说明书"——同一段 user 消息,不同的 system prompt 会得到截然不同的回答。

🎭 贯穿本教程的「任务助手 Agent」 就是通过 system prompt 定义的: 它被设定为一个"简洁、高效的任务管理助手",只回答任务相关的问题。


3. Tokens 与计费

LLM 不是按"字数"收费,而是按 token 收费。

什么是 Token?

Token 是模型处理文本的最小单位。大致规律: - 英文:1 个单词 ≈ 1–1.5 个 token - 中文:1 个汉字 ≈ 1.5–2 个 token - 代码:变量名、符号各占 token

"Hello world"       → 2 tokens
"你好世界"          → 2–3 tokens
"def hello():"      → 4 tokens

为什么 Token 重要?

  1. 计费:API 按输入 token + 输出 token 分别计价
  2. 上下文窗口:模型能"看到"的 token 总量有限(下一节)
  3. 速度:输出 token 越多,等待越久

Token 用量在哪里看?

API 响应里有 usage 字段,精确告诉你用了多少 token:

{
  "usage": {
    "prompt_tokens": 25,      // 输入(你的 messages)用了多少 token
    "completion_tokens": 48,  // 输出(模型的回答)用了多少 token
    "total_tokens": 73        // 合计
  }
}

本章代码会打印这个字段,让你亲眼看到每次调用的 token 消耗。


4. 上下文窗口(Context Window)

每个模型有一个上下文窗口限制——即它一次能处理的最大 token 总数(输入 + 输出)。

模型 上下文窗口 约等于
GPT-4o-mini 128K tokens ~10 万字中文
DeepSeek-Chat 128K tokens ~10 万字中文
Qwen-Plus 128K tokens ~10 万字中文
GPT-4o 128K tokens ~10 万字中文

超了会怎样?

如果你的 messages 总 token 超过窗口限制: - API 会返回 400 错误("context length exceeded") - 不会"自动截断"——你得自己处理

这对 Agent 意味着什么?

Agent 需要把整个对话历史塞进 messages。随着对话变长,历史消息会占满窗口。 解决方案(第05章讲):摘要、截断、滑动窗口。

⚠️ 反模式:以为模型"记住"了之前的对话。其实每次请求都是独立的—— 你能传多少历史消息,完全取决于你手动塞了多少进 messages 数组。


5. 温度与采样参数(Temperature & Sampling)

temperature 控制模型输出的"随机性":

temperature 行为 适用场景
0.0 几乎确定性,每次输出相同 代码生成、数据提取、分类
0.3 轻微随机 日常问答、摘要
0.7 中等随机 创意写作、头脑风暴
1.0 高随机性 诗歌、故事、发散思维

原理(简化版)

模型在每一步不是直接选"最可能的下一个 token",而是从一个概率分布中采样。 温度越高,概率分布越"平坦"——低概率的 token 也有机会被选中,输出就更多样。

temperature = 0.0  →  总是选概率最高的 token  →  确定性输出
temperature = 1.0  →  按原始概率采样          →  多样化输出

本章代码会让同一个问题分别用 0.01.0 跑一次,让你对比差异。

其他采样参数(了解即可)

  • top_p(nucleus sampling):另一种控制随机性的方式,和 temperature 二选一调。
  • max_tokens:限制输出最大 token 数,防止单次调用太贵。
  • stop:指定停止词,模型遇到就停(比如 "\n")。

本章只用 temperature,其余参数后续章节按需引入。


6. 流式 vs 非流式响应

非流式(默认)

API 等模型生成完全部 token 后,一次性返回完整响应。

发送请求  →  等待 3 秒  →  收到完整回答

优点:简单,拿到完整 JSON。 缺点:用户盯着空白屏幕等 3 秒,体验差。

流式(stream=True

API 边生成边返回,每生成几个 token 就发一个 chunk。

发送请求  →  收到 "你"  →  收到 "好"  →  收到 ","  →  …  →  收到 [DONE]

优点:用户立刻看到输出逐字出现,体验好。 缺点:代码稍复杂,需要处理 chunk 流。

什么时候用哪个?

场景 推荐
脚本/批处理 非流式(简单)
对话 UI/聊天机器人 流式(用户体验)
需要拿 usage 统计 非流式(流式时 usage 可能不全)
Agent 循环内部调用 非流式(代码简单,不需要实时显示)

本章两种都演示,后续章节根据场景选择。


7. 反模式与常见误解

❌ "模型会记住之前的对话"

真相:每次 API 调用都是独立的。模型没有任何"记忆"。 你能传多少历史,取决于你手动把多少消息塞进 messages 数组。 → 多轮对话的记忆管理是第05章的内容。

❌ "模型会精确算术"

真相:LLM 是概率模型,不是计算器。它可能算对 2+2,但对 123456 × 789 大概率出错。 需要精确计算时,应该让模型调用工具(如 Python 解释器)。 → 工具调用是第03章的内容。

❌ "上下文窗口越大越好"

真相:大窗口不等于高质量。塞太多无关信息反而会稀释关键内容("lost in the middle" 问题)。 好的 Agent 需要上下文工程——精选哪些信息该进窗口。 → 上下文管理是第05、14章的内容。

❌ "temperature=0 就是100%确定"

真相:即使 temperature=0,模型在底层浮点运算中仍有微小随机性(取决于硬件/实现)。 但实际差异极小,可以认为是"确定性"的。

常见错误

概念懂了,实际写代码还是会踩坑。这些是初学者最常犯的错误。

错误 症状 解决
忘记传 API Key AuthenticationError: Invalid API key 或 HTTP 401 检查 .env 文件中 OPENAI_API_KEY 是否填写,确认没有多余空格
上下文窗口超限 context_length_exceeded HTTP 400 错误 检查 messages 总 token 数,用响应中的 usage 字段监控,必要时截断历史
temperature 设错场景 分类任务每次结果不同,或创意写作千篇一律 代码生成/分类用 0.0,创意任务用 0.71.0
流式响应没处理 [DONE] 程序卡住不退出,或拼接出乱码 检查 chunk 是否为 [DONE] 再停止循环,拼接时用 chunk.choices[0].delta.content

8. 本章代码结构

01-llm-basics/
├── README.md          ← 你在这里
├── python/
│   ├── main.py        ← Python 演示代码
│   └── requirements.txt
├── typescript/
│   └── main.ts        ← TypeScript 对等实现
└── exercises/
    └── README.md      ← 练习与参考答案

运行

# Python
cd ai-agent/01-llm-basics
python3 python/main.py

# TypeScript
npx tsx typescript/main.ts

两者输出内容等价:单轮对话 → token 用量 → 温度对比 → 流式输出。


9. 知识检查清单

学完本章,你应该能回答:

  • [ ] Chat Completions API 的 messages 数组里有哪些角色?各自作用?
  • [ ] prompt_tokenscompletion_tokens 分别指什么?
  • [ ] 上下文窗口超了会怎样?
  • [ ] temperature=0temperature=1 的区别?
  • [ ] 流式响应的适用场景?
  • [ ] 为什么模型不会"记住"之前的对话?

下一章第02章 · Prompt 工程 —— 学会用 system prompt 精确控制模型行为。

阅读更多

AI Agent 进阶教程 — 从零到生产(Python + TypeScript)

一句话:从最原始的 API 调用出发,自己从零造一个 mini Agent 框架, 再切换到现代框架——学完后,无论流行什么框架你都能快速上手,知识不过时。 全程 Python + TypeScript 双语言并列,OpenAI 兼容接口可一键切换提供商。 为什么有这个教程 市面上的 Agent 教程大多有两个毛病: "先工具后原理":上来就教你调 LangChain 的 AgentExecutor,一行代码跑起来很爽, 但出 bug 时完全不知道哪里错了。框架一旦过时,你的知识也跟着报废。 玩具示例:清一色 "Hello World Agent",看完不会写真实的 Agent。 本教程反其道而行: 🧭 先原理后工具 先看清原理,再选择工具。 原理是不变的,工具是流动的。

作者:zhangsheng

第02章 Prompt 工程 — 让 LLM 精准听话

本章是「任务助手 Agent」的第一次能力升级:从"随便聊聊"变成"精准执行任务"。 我们会用原生字符串模板(f-string / 模板字符串)手写 4 种核心 Prompt 技术, 不依赖任何第三方抽象库。 TL;DR 30 秒速读:Prompt 工程的四种核心技术是 System Prompt(定身份)、Few-shot(给示例教模式)、Chain-of-Thought(引导逐步推理)、结构化输出(强制 JSON),它们是所有 Agent 指令设计的基础。 如果只记一件事:system prompt 的优先级高于 user message,

作者:zhangsheng

第03章 工具调用(Tool Use / Function Calling)

「任务助手 Agent」获得了"手"——它能调用工具查天气、做计算、搜百科,不再只是空谈。 TL;DR 30 秒速读:LLM 本身不能执行任何代码,所谓"工具调用"是模型输出一段 JSON 指令,由你的客户端解析并执行,再把结果反馈给模型。 如果只记一件事:工具的 description 写得越清晰,模型选择工具越准确;写"处理数据"不如写"查询指定城市的当前天气,返回温度和天气状况"。 本章目标 学完本章,你将理解: 工具调用的本质:LLM 不直接执行工具,而是输出结构化指令(JSON),由客户端执行 JSON Schema

作者:zhangsheng

第04章 Agent 循环(The Agent Loop)

「任务助手 Agent」获得了"自主性"——从第03章的"单轮调用工具",进化为"多步循环调工具直到完成任务"。 这是本教程的核心概念:单轮=工具调用,多轮=Agent。 TL;DR 30 秒速读:Agent 循环就是一个 for 循环,每轮让 LLM 决定下一步行动、执行工具、把结果反馈回去,直到模型不再调用工具或达到 max_steps 上限。 如果只记一件事:永远给 Agent 循环加 max_steps 上限(建议 10 到 20),没有上限的循环是生产事故的源头,一个失控 Agent

作者:zhangsheng