向量与余弦相似度:RAG 背后的数学地基
2026/8/28 15:49:31 网站建设 项目流程

向量与余弦相似度:RAG 背后的数学地基

文档加载完了,切成小块了——然后呢?用户问"怎么优化 SQL 查询",你总不能把所有文档块都扔给模型吧?Token 爆炸不说,模型也看不过来。解决思路是:先找到和问题最相关的文档块,再喂给模型。而这个"找最相关"的能力,靠的就是向量和余弦相似度。本文零公式恐惧,用直觉和代码讲透这两个概念。


一、RAG 到底在干什么?——先把全貌装进脑子

先搞清楚 RAG(Retrieval-Augmented Generation,检索增强生成)的完整流程:

这个流程里,最关键的就是第②步——怎么判断"哪段文档和问题最相关"。答案就是:向量 + 余弦相似度

RAG 的活儿就一句话:先把"相关的料"挑出来,再让模型"照着料说话"。挑料挑得准不准,直接决定回答质量。


二、向量是什么?——给文字贴一个"GPS 坐标"

2.1 直觉理解——每个句子都有自己的"经纬度"

想象每段文字都有一个 GPS 坐标:

  • "苹果好吃" → 坐标 A

  • "我喜欢吃苹果" → 坐标 B(和 A 很近)

  • "今天下雨了" → 坐标 C(和 A、B 都很远)

语义相近的文字,坐标也相近。这就是向量嵌入(Embedding)的核心思想。

嵌入模型 = 给文字发 GPS 的"定位员"。它把一句话变成一个坐标点,语义越接近,坐标靠得越近。

2.2 用代码感受一下——定位员是怎么工作的

from langchain_openai import OpenAIEmbeddings ​ embeddings = OpenAIEmbeddings(model="text-embedding-3-small") ​ # 把文字变成向量(一串数字) vec1 = embeddings.embed_query("苹果是一种很好吃的水果") vec2 = embeddings.embed_query("我喜欢吃苹果") vec3 = embeddings.embed_query("今天下雨了") ​ print(f"向量维度:{len(vec1)}") # 1536 维 print(f"前 5 个数字:{vec1[:5]}") # [0.0123, -0.0456, 0.0789, -0.0234, 0.0567]

向量就是一个高维坐标。1536 维听起来吓人,但你可以把它想象成有 1536 个坐标轴的 GPS——每个轴代表一种语义方向,比如"水果程度"、"天气程度"、"积极程度"……


三、余弦相似度:衡量两个向量"有多近"

有了坐标,怎么算两个点之间的距离?这里不用欧几里得距离(直线距离),而是用余弦相似度——衡量两个向量方向的接近程度,而不是绝对距离。

3.1 直觉理解——比的是"方向"不是"远近"

  • vec1 和 vec2 方向几乎一致 → 余弦相似度接近 1 → 语义相近

  • vec1 和 vec3 方向完全不同 → 余弦相似度接近 0 → 语义不同

余弦相似度看的是"你俩朝一个方向走吗",而不是"你俩隔了几公里"。同一篇文章的长短版,方向一致,相似度照样高。

3.2 动手算一下——自己写个 10 行公式

import numpy as np ​ def cosine_similarity(vec_a, vec_b): """计算两个向量的余弦相似度""" dot_product = np.dot(vec_a, vec_b) norm_a = np.linalg.norm(vec_a) norm_b = np.linalg.norm(vec_b) return dot_product / (norm_a * norm_b) ​ # 计算相似度 sim_12 = cosine_similarity(vec1, vec2) # "苹果好吃" vs "我喜欢吃苹果" sim_13 = cosine_similarity(vec1, vec3) # "苹果好吃" vs "今天下雨了" ​ print(f"vec1 vs vec2 相似度:{sim_12:.4f}") # 0.85 左右,很相似 print(f"vec1 vs vec3 相似度:{sim_13:.4f}") # 0.30 左右,不太相似

3.3 余弦相似度的取值范围——给你一把"打分尺"

含义示例
1.0方向完全一致"你好" vs "你好"
0.7~0.9高度相关"苹果好吃" vs "我喜欢吃苹果"
0.3~0.5有一定关联"苹果好吃" vs "水果有营养"
0.0~0.2基本无关"苹果好吃" vs "今天下雨了"

余弦相似度的核心优势:它只关心方向,不关心长度。一篇 100 字的文章和一篇 10000 字的文章,如果语义相同,余弦相似度依然很高。欧几里得距离做不到这一点。


四、实战:用余弦相似度做一个迷你搜索引擎

纸上谈兵没用,咱们直接手写一个迷你搜索引擎,感受一下"找最相关文档"到底是怎么回事。

from langchain_openai import OpenAIEmbeddings import numpy as np ​ embeddings = OpenAIEmbeddings(model="text-embedding-3-small") ​ # 知识库(文档块) documents = [ "SQL 查询优化:使用索引可以大幅提升查询速度", "Python 装饰器是一种高阶函数,用于修改函数行为", "数据库索引类型:B-Tree 索引、Hash 索引、全文索引", "Docker 容器化部署:编写 Dockerfile 的最佳实践", "MySQL 慢查询分析:使用 EXPLAIN 查看执行计划", ] ​ # 把所有文档向量化 doc_vectors = [embeddings.embed_query(doc) for doc in documents] ​ # 用户问题 query = "怎么优化 SQL 查询" query_vector = embeddings.embed_query(query) ​ # 计算余弦相似度 def cosine_sim(a, b): return np.dot(a, b) / (np.linalg.norm(a) * np.linalg.norm(b)) ​ # 对每个文档计算相似度 scores = [cosine_sim(query_vector, dv) for dv in doc_vectors] ​ # 排序,取 Top 3 ranked = sorted(zip(scores, documents), reverse=True)[:3] ​ for score, doc in ranked: print(f"相似度 {score:.4f} | {doc}")

输出效果:

相似度 0.8901 | SQL 查询优化:使用索引可以大幅提升查询速度 相似度 0.8234 | MySQL 慢查询分析:使用 EXPLAIN 查看执行计划 相似度 0.7654 | 数据库索引类型:B-Tree 索引、Hash 索引、全文索引

看到了吗?"怎么优化 SQL 查询"这个自然语言问题,自动把"SQL 优化"、"慢查询"、"索引"这三篇最相关的文档找出来了。这就是 RAG 的检索核心。


五、为什么不用关键词匹配?——"认字" vs "懂意思"

你可能会问:直接用if "SQL" in doc做关键词匹配不行吗?来看一个对比:

用户问题关键词匹配语义匹配(向量)
"怎么加快数据库查询速度"找不到"SQL"关键词,漏掉找到 SQL 优化相关文档 ✓
"iPhone 怎么修"找不到"苹果"关键词找到 Apple 维修文档 ✓
"如何减肥"精确匹配"减肥"也匹配到"瘦身"、"减脂"相关内容 ✓

关键词匹配是"认字",语义匹配是"懂意思"。向量检索不受同义词、近义词的限制,这也是为什么 RAG 比传统搜索强大得多。


六、嵌入模型选型:云端 vs 本地——按场景挑"定位员"

迷你搜索引擎跑通了,接下来要上规模了。嵌入模型选哪个?先看一张对比表:

模型维度语言部署方式一句话推荐
text-embedding-3-small1536多语言OpenAI 云端综合首选,性价比高
text-embedding-3-large3072多语言OpenAI 云端精度要求高时用
bge-large-zh-v1.51024中文本地部署纯中文场景,本地跑
nomic-embed-text768英文Ollama 本地本地开发测试
# 本地嵌入模型(Ollama) from langchain_ollama import OllamaEmbeddings ​ embeddings = OllamaEmbeddings(model="nomic-embed-text") vec = embeddings.embed_query("你好世界") print(len(vec)) # 768 维

云端省事、本地省钱,关键看你的数据能不能出内网。折腾原型用云端,数据敏感就老老实实本地跑。


七、总结——一张表 + 一句金句

概念一句话
向量嵌入把文字变成一串数字(坐标),语义相近的文字坐标也相近
余弦相似度衡量两个向量"方向"的接近程度,值越接近 1 越相似
嵌入模型负责做"文字→向量"转换的模型
RAG 检索用余弦相似度从知识库中找最相关的文档块

向量 + 余弦相似度 = RAG 的数学地基。不需要懂数学公式,只需要理解"同类文字向量方向接近"这个直觉,就足以理解 RAG 的工作原理了。下一篇,我们把这个迷你搜索引擎升级成真正的向量存储与检索系统——百万级文档也照样秒查。


参考资料

  • OpenAI Embeddings 文档

  • 余弦相似度 - 维基百科

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询