最近在看大模型应用开发,发现很多 AI 层的概念其实和传统编程的数据结构是相通的。今天把 Python 字典、哈希表以及 Prompt 设计规则整理一下,顺便理一理 LLM API 调用的基础封装。
Dict 与 HashTable:为什么查找能这么快?
在 JS 里我们习惯了对象字面量 {key: value},ES6 又引入了 Map 和 Set。到了 Python,对应的就是 dict(dictionary)。
dict 最核心的优势在于 O(1) 的时间复杂度。这就像查字典一样,通过偏旁或字母索引直接定位,而不需要从第一个字翻到最后一个字 O(n)。
如果没有 dict 会怎样?
假设要根据同学的名字查找成绩,不用字典的话,通常的做法是用两个列表:一个存名字,一个存成绩,靠下标对应。但每次查找都需要遍历整个列表,效率极低。
HashTable 的本质
dict 之所以快,是因为底层基于哈希表(HashTable) :
- Key 是唯一的,经过哈希函数运算后得到一个唯一索引。
- 索引指向存储位置,里面放着对应的 Value。
- 查找时,直接用 Key 算出索引,一步到位拿到 Value。
这种结构的特点是:查找和插入极快,不随 Key 的增加而变慢;但代价是占用大量内存。
与之相反的是 List:查找和插入时间随元素增加而增加,但省内存。所以 dict 适合用在需要高速查找的场景,本质上是空间换时间。
Unhashable Type:为什么 List 不能做 Key?
dict 的 key 必须是可哈希的(hashable) ,通俗讲就是不可变类型。
如果你写 key = [1,2,3],列表是可变的,内容随时可以添加或删除。而 hash 算法要求同一个 key 每次计算出的结果必须一致——如果 key 变了,算出来的存储位置就不同了,整个 dict 的结构就乱了。
这也是为什么字符串可以做 key:'abc' 是不可变对象,调用 'abc'.replace('a', 'A') 并不会改变原对象,而是返回一个新的 'Abc'。变量可以被重新赋值,但字符串对象本身的内容永远不变。
Set:没有 Value 的 Dict
set 和 dict 原理完全一样,也是一组 key 的集合,区别仅仅在于 set 不存储对应的 value。因为 key 不能重复,所以 set 天然去重。
Prompt 设计的核心原则
回到大模型应用,Prompt 的设计其实也有明确的规则:
- 撰写清晰、具体的指令:让模型的回答符合预期,不偏离主题。尽量提供完整的说明和背景信息(上下文),而不是丢一句模糊的问题过去。
- 引导逐步推理:对于复杂任务,让模型一步步思考,而不是直接给最终答案。
这和写代码的逻辑很像——你给机器的指令越明确,它执行得越准确。
LLM API 调用封装
在实际工程中,通常会封装一个 get_response(prompt, model='...') 函数。几个关键参数:
- temperature:控制随机性。0 最确定(适合严谨任务),1 最随机(适合创意生成),0.5 居中。
- max_tokens:限制生成的最大 token 数,防止输出过长或失控。
Python 的 f-string 多行语法 f"""...""" 在这里非常实用,可以直接当字符串模板用,嵌套变量也很方便。
顺带一提,JS 里的函数提升(hoisting)机制也值得注意:函数声明优先于变量提升,如果定义了同名函数,后面的会覆盖前面的。这和 Python 中变量的作用域规则有些不同,跨语言开发时容易踩坑。
从 Python Dict 到 LLM Prompt:前端转 AI 的底层逻辑笔记