Skip to content
Stack Ashes
Go back

我是怎么理解余弦相似度的

最近在补 RAG 的基础,绕不开一个词:cosine similarity,中文一般叫 余弦相似度

说实话,一开始我对这个词挺抗拒的。它看起来像是那种“你要先补线性代数才能继续往下看”的概念。尤其是看到 cosine、vector、embedding、dot product 这些词堆在一起时,很容易有一种感觉:我只是想知道 RAG 怎么查资料,怎么突然开始上数学课了。

但看了一圈之后,我发现如果只是为了理解 RAG 里的检索,余弦相似度没有那么吓人。它背后的直觉其实很朴素:

把两段文字都变成向量,然后看这两个向量是不是朝着差不多的方向。

方向越像,通常说明它们语义越接近。

这篇不是严格数学推导,更像是我自己的理解笔记。如果你也刚开始看 RAG、embedding、向量数据库,希望这篇能帮你少绕一点路。

余弦相似度看的是向量方向

我最开始卡住的地方

我之前一直有个误解:既然是“相似度”,那是不是就是看两个东西离得近不近?

比如两个点在图上,距离越短,就越相似。这个想法当然也没错,很多算法确实会用距离来衡量接近程度。但余弦相似度稍微不一样,它更关心的是“方向”,不是单纯的距离,也不是长度。

可以想象两个人从同一个地方出发。

一个人往东北走得很远,另一个人也往东北走,只是走得短一点。虽然他们走的距离不一样,但方向是一致的。

如果另一个人往西南走,那就算他走的距离差不多,也明显不是一回事。

余弦相似度看的就是这种感觉。

它想问的不是:

谁更长?谁数值更大?

而是:

它们是不是大概指向同一个方向?

这个直觉一旦建立起来,后面的公式就没那么难受了。公式只是把这个“方向像不像”变成一个分数。

文字为什么能比较方向?

这里还有一个前提:文字要先变成向量。

计算机没法直接理解一句话的意思。它看到的是字符、token、数字。为了让机器能比较“这句话和那句话是不是意思接近”,我们通常会用 embedding 模型把文本变成一串数字。

比如一句话:

RAG 是什么?

模型会把它变成一串数字,大概长这样:

[0.12, -0.35, 0.88, 0.04, ...]

这串数字不是给人看的,是给机器算的。你可以把它理解成这句话在“语义空间”里的一个位置,或者一个方向。

另一句话:

大模型怎么先查资料再回答?

它字面上和“RAG 是什么”不太一样,但意思可能很接近。embedding 模型如果做得不错,这两句话对应的向量方向就会比较接近。

这也是向量检索比纯关键词搜索有意思的地方:它不只看有没有同一个词,还试图看背后的意思是不是接近。

比如你搜索“怎么让 AI 看文档回答问题”,文档里可能写的是“Retrieval Augmented Generation”。关键词完全对不上,但语义上是在说同一个东西。向量检索就有机会把它找出来。

当然,这里我也不想把它说得太神。embedding 模型不是永远懂你,它只是把文本压成了一组数字表示。这个表示好不好,直接决定后面相似度算得准不准。

如果 embedding 本身就把意思表示歪了,余弦相似度算得再认真,也只是认真地算错。

一个小例子:口味相似

为了让这个更具体一点,可以先不用文本,想一个简单的口味例子。

假设我们只用两个维度来描述一个人的口味:

[喜欢甜的程度, 喜欢辣的程度]

小明是:

[9, 1]

小红是:

[8, 2]

小刚是:

[1, 9]

你大概一眼就能看出来,小明和小红更像。他们都偏甜口。小刚就不一样,他明显偏辣口。

如果把这些点从原点画成箭头,小明和小红的箭头方向会很接近,小刚的方向就偏得多。

这就是余弦相似度想捕捉的东西。

真实的文本向量当然不会只有两个维度。它可能有几百维、几千维。每一维也不是“甜”或者“辣”这么好解释。但直觉类似:模型把文本放进一个高维空间里,语义接近的文本会有相似的方向。

我们看不懂那个空间,但机器可以在里面计算。

公式不用背,但可以看一眼

余弦相似度的公式是:

cosine_similarity(A, B) = A · B / (||A|| × ||B||)

第一次看会觉得烦。

但如果只保留直觉,它就是在算两个向量夹角的 cos 值。

大概可以这样记:

接近 1:方向很像
接近 0:关系不大
接近 -1:方向相反

其中 A · B 是点积,||A||||B|| 是两个向量的长度。分母把长度的影响除掉了,所以最后更关注方向。

这也是为什么它叫“余弦”相似度。它不是凭空来的,而是来自几何里的夹角。

在文本检索里,我们多数时候不用特别纠结每个分数的绝对意义,只要比较谁更高。

比如用户问:

RAG 的三个阶段是什么?

资料库里有三段:

chunk 1:RAG 包括 ingestion、retrieval 和 synthesis。
chunk 2:Prompt engineering 是设计提示词的方法。
chunk 3:模型微调可以让模型适应特定任务。

算出来可能是:

问题 vs chunk 1 = 0.91
问题 vs chunk 2 = 0.35
问题 vs chunk 3 = 0.28

那系统就会优先拿 chunk 1。

相似度分数示例

放到 RAG 里,它其实只是一个“找资料”的环节

RAG 这件事,如果说得朴素一点,就是让大模型回答之前先查资料。

但资料库可能很大,不可能每次把所有文档都塞给模型。比如一个公司的内部知识库,可能有产品文档、接口说明、会议记录、FAQ、故障复盘。用户问一句话,你不可能把全部内容都丢进 prompt。

所以中间需要一个检索步骤:先从一堆资料里挑出几段最可能有用的。

流程大概是:

文档切块
每个块变成向量
用户问题也变成向量
用余弦相似度找方向最接近的几个块
把这些块交给大模型回答

余弦相似度在 RAG 中的位置

所以余弦相似度不是那个“生成答案”的东西。

它更像一个检索员。你问了一个问题,它先去资料库里翻一翻,挑几段它觉得可能相关的内容出来。后面怎么组织语言、怎么回答,那是大模型的事。

这个区分对我还挺重要的。因为一开始学 RAG 的时候,很容易把所有能力都归到 LLM 身上,好像模型什么都懂。其实很多时候,答案好不好,前面检索有没有找对资料,占了很大一部分。

如果检索拿错了材料,大模型写得再流畅,也只是在错误材料上发挥。

这也是为什么很多 RAG 问题,不一定是“模型不够强”,而是“资料没找对”。

关键词搜索和向量搜索不是敌人

还有一点我后来才慢慢理解:向量搜索不是用来完全取代关键词搜索的。

关键词搜索很直接,也很可靠。你搜一个错误码、函数名、配置项、产品编号,它往往比向量搜索更准。因为这些东西需要精确匹配,不是语义差不多就行。

但向量搜索擅长处理表达方式不一样、意思差不多的情况。

比如:

用户:为什么模型会胡说八道?
文档:LLM hallucination refers to generated content that is factually incorrect...

关键词不一定能命中,但向量可能觉得它们很接近。

所以真实系统里经常会做 hybrid search,也就是关键词搜索和向量搜索一起用。先从两个角度各找一批候选,再合并、重排。

这件事也提醒我:很多工程问题不是选一个“最先进”的方法,而是把几个朴素的方法组合好。

它好用,但别迷信

我觉得学习这类概念时,很容易走到两个极端。

一个极端是觉得公式太难,干脆不碰。

另一个极端是觉得只要用了向量、用了 cosine similarity,系统就智能了。

这两个都不太对。

余弦相似度确实很实用,但它只是一个相似度度量。它不会真正理解你的业务,也不会判断资料是否权威,更不会自动保证答案正确。

它至少有几个限制。

第一,embedding 表示不好,相似度也会跟着错。比如模型不擅长中文,或者对某个专业领域不熟,生成出来的向量可能就不靠谱。

第二,相似不等于有用。某段内容可能和问题主题相关,但并没有回答问题。用户问“RAG 常见失败点有哪些”,系统可能找到一段“RAG 是什么”。它相关,但不够有用。

第三,它只是在找候选资料,不是在做完整推理。真正要判断答案是否充分、是否引用正确、是否覆盖问题,还需要后面的模型、prompt、rerank、评估一起配合。

所以真实的 RAG 系统里,后面往往还会有 rerank、过滤、引用、评估这些步骤。余弦相似度只是入口,不是终点。

我现在会怎么记它

如果让我用一句话给自己记笔记,我会写:

余弦相似度是在比较两个向量的方向,方向越接近,通常表示语义越相近。

如果放到 RAG 里,再补一句:

它负责帮系统从资料库里先挑出几段可能相关的内容。

就这样。

不需要把它神化,也不需要被公式吓住。

它只是 AI 系统里一个很基础的零件。理解它之后,再去看 embedding、向量数据库、RAG 检索,就会踏实很多。至少你会知道,所谓“语义搜索”,中间有一部分其实就是在做这样一件朴素的事:

把问题和资料都变成向量,然后看看谁和谁方向更像。

我觉得这也是学习 AI 工程里比较有意思的地方。很多听起来很抽象的词,拆开以后并不神秘。它们不是魔法,只是一层一层的小机制叠起来。

余弦相似度就是其中一个小机制。它不炫技,但很常用。懂了它,再看 RAG,就不会只停留在“模型会查资料”这种模糊印象上,而是能看到中间那一步具体是怎么发生的。


Share this post on:

Previous Post
339 个子代理烧光额度后,我发现 AI Agent 真正缺的不是模型
Next Post
2-5 年职业发展规划