大家好,我是你们的搜索技术观察员。今天想聊一个最近在 Hacker News 上热度很高的技术话题:“Show HN: A new type of search engine”。
看到这个标题,很多人的第一反应可能是:搜索引擎还能玩出什么新花样?Google 已经把关键词匹配做到了极致,Vector Search(向量检索)也被各种数据库厂商讲烂了,RAG 更是把“聊天式搜索”变成了标配。新东西还能解决什么痛点?
我的判断是:这次热的不是某个具体产品,而是搜索范式的转向。新一批“新类型”搜索引擎,不再纠结于“怎么更快地找到包含关键词的网页”,而是转向“怎么帮你完成一个任务”。它们把搜索从“信息匹配工具”重新定义为“任务理解与执行引擎”。
这篇文章不想去复述某个特定项目的官网介绍(HN 原贴信息有限,且不可查证),而是想结合当前搜索技术演进的方向,把这个“新类型”到底新在哪讲透。我们会从传统搜索的架构瓶颈讲起,分析 RAG、Agentic Search、Graph-based Search 几个主要方向的核心差异,最后用一个最小可跑的 Python 示例,带你从零搭一个具备“新型搜索”雏形的本地语义搜索引擎——技术老鸟可以直接跳到第 5 节看代码,但建议从头读,因为真正值钱的是概念之间的边界。
1. 新型搜索引擎到底解决了什么老问题
先把结论放在前面:传统搜索引擎解决的是“快速定位已存在信息”的问题,而新型搜索引擎试图解决“快速生成一个可验证答案”的问题。这两者的差别,是“查询”和“任务”之间的差别。
举个具体例子。你要写一份关于“2025年初级程序员薪资趋势”的报告。传统搜索引擎的工作方式是:你输入“2025 初级程序员 薪资”,它返回一万条招聘网站的链接;你一个个点开,从一个页面里复制一段,再回到搜索框,输入“2025 程序员 薪资 变化”,继续翻下一个页面。整个流程大约需要半小时,其中大部分时间花在“打开-扫视-关闭”的循环上。
新型搜索引擎的工作方式是:它先理解你输入的自然语言背后是一个“调研任务”,然后自动把任务拆解成若干个检索子步骤:
- 查询各城市初级程序员薪资中位数;
- 查询与去年同期相比的涨幅;
- 查询不同技术栈的薪资差异;
- 把这些信息汇总成一个带引用来源的结构化报告。
两者的架构差异决定了体验差异。传统搜索是无状态的单次检索,它不记得你之前搜索过什么,也不关心你最终要完成什么;新型搜索则在引入任务状态记忆和多步推理,它在尝试“参与任务完成过程”,而不仅仅是“提供素材入口”。
从工程角度看,这意味着传统搜索引擎的架构核心是“倒排索引 + 关键词相关性排序”,而新型搜索引擎的架构核心是“意图解析 + 多路召回 + 语义重排 + 生成组装”。核心矛盾从“索引规模”转移到了“意图理解与信息可信度控制”。
这也是为什么最近几年“Search-as-a-Service”概念重新热起来。不是因为 Google 不好用了,而是“好用”的定义变了。过去,输入关键词-看到链接是一种“可用”;现在,对于大量用户来说,直接得到一个带引用来源的答案才是“好用”。
2. 传统搜索引擎的架构边界:关键词匹配能做到什么程度
要理解“新类型”到底新在哪,得先弄清楚传统架构的能力边界。这里用最小化模型来讲解。
传统搜索引擎由三个核心部件构成:
- 爬虫:负责从网络上抓取页面内容;
- 倒排索引:把“页面-关键词”关系反转成“关键词-页面列表”,便于快速根据关键词查找到所有相关页面;
- 相关性排序:根据 TF-IDF、BM25 等算法计算查询词和页面的匹配度,输出排序结果。
这套架构从 1990 年代成型到现在,仍然是所有主流搜索引擎的底层骨架。它的优势非常明显:成熟、稳定、可水平扩展、性能极高。但它有一个天然的语义缺陷:它做的是词汇层面的匹配,不是语义层面的理解。
比如用户搜“怎么把大象放进冰箱”,传统搜索引擎能精准找到包含这几个字的所有页面,但它理解不了“这其实是一个冷幽默段子”。同样,用户输入“跑鞋 耐磨 评测”,它能返回一堆包含关键词的网页,但无法直接回答“哪款跑鞋在 5 公里日常训练中最耐磨”。
这个缺陷在过去并不致命,因为网页本身就是信息载体,用户点到详情页后可以自己完成信息筛选。但在今天,内容总量呈指数级增长,信息噪声比(Noise-to-Signal Ratio)急剧上升。用户不再愿意花 20 分钟从 20 个页面里手动归纳答案。搜索的瓶颈从“索引覆盖度”变成了“信息消化成本”。这就是新型搜索引擎切入的生态位。
传统架构还有一个重要限制:它无法理解用户的连续性意图。你在搜索“长沙天气”之后紧接着搜“明天呢”,系统不知道“明天呢”指代的是“长沙明天的天气”。这种跨轮次指代消解,需要维护一个会话上下文——传统搜索引擎为了保持性能,往往会主动放弃这一点。
所以严格来说,传统搜索引擎不是“笨”,它是被自己的架构目标锁死了:它在设计上优先保证“任何关键词在任何规模下都能 10ms 内返回结果”,而不是“理解用户此刻真正想要什么”。当检索成本已经不是问题,而理解成本成为主要矛盾时,新技术就有了生存空间。
3. 当前“新类型”搜索的主要技术路线与对比
从目前业界的研究和开源项目来看,所谓“新类型搜索”,大致可以分为以下四条技术路线。它们之间不是互斥的,很多实际产品会混合使用。
3.1 RAG(检索增强生成)路线
这是目前落地最广的路线。核心思想是:不直接让大语言模型凭记忆回答问题,而是先从知识库中检索出相关片段,再把片段拼进 Prompt 让模型基于这些片段生成答案。
优点是答案可以有引用来源,可以对接企业内部私有知识库,相对不容易出现大模型“一本正经胡说八道”的情况。缺点是:检索质量直接决定答案质量。如果召回阶段没有找到正确的片段,大模型再强也只能借用上下文中的错误信息回答。
3.2 Agentic Search(智能体式搜索)路线
这是当前最热的方向,也是“Show HN: A new type of search engine”这类标题下最高频出现的实现方式。
它的核心区别在于:搜索系统从“一次性问答”升级为“自主规划+多步执行”。
一个典型的 Agentic Search 流程如下:
- 接收用户的复杂问题;
- 由 LLM 规划出子任务列表;
- 每个子任务调用不同的检索工具(网页搜索、文档库、数据库、代码仓库);
- 汇总所有子任务结果;
- 生成最终答案并列出引用来源。
这条路线真正的新意在于,它把搜索从“单条查询”扩展为“一个有状态的任务循环”。系统内部会记录已经获取的信息,判断哪些信息仍缺失,然后主动发起下一轮检索。它更像一个“会查阅资料的实习生”,而不是“一本印刷好的目录”。
从工程架构看,Agentic Search 需要引入三个传统搜索没有的组件:
- 任务规划器:把主问题拆解为子问题;
- 工具调用协议:让模型能够调用外部 API(Web Search、数据库、代码解释器等);
- 记忆机制:保存中间检索结果,供后续步骤复用。
3.3 向量检索与语义搜索
这条路线的核心是用 Embedding 模型把文本转成向量,通过向量相似度来检索语义相近的内容。它解决了传统搜索引擎的一个核心痛点:查询词与文档用词不一致时,传统关键词匹配会失败,而向量匹配依然可能命中。
例如,用户搜“怎么治疗打嗝”,文档写的是“膈肌痉挛缓解方法”,传统搜索引擎的 BM25 匹配可能失败,但两者的语义向量距离很近,向量检索可以轻松召回。
缺点是:向量检索在精确匹配、数值范围查询、布尔过滤上表现不佳。所以现在的主流做法是“混合检索”:把传统 BM25 与向量召回同时执行,再用一个重排模型(Reranker)合并打分。这已经是当前企业级知识库问答的标配架构。
3.4 Graph-based Search(图结构搜索)
这条路线相对小众,但在企业知识库和垂直领域内很有价值。它的核心思想是:不仅搜索文本内容,还搜索实体之间的关系。
比如搜索“A 部门和 B 部门之间有哪些人参与了同一个项目”,传统搜索和向量搜索都很难直接回答,因为这涉及到实体关系和路径遍历,属于图数据库擅长的问题。架构上可以理解为“知识图谱 + 图数据库 + LLM 转译层”的组合。
为了更直观地对比这四条路线,以下给出参考表格:
| 技术路线 | 核心原理 | 解决的核心痛点 | 主要局限 | 典型适用场景 |
|---|---|---|---|---|
| 传统关键词搜索 | 倒排索引 + BM25 | 大规模网页快速检索 | 无法理解语义与任务意图 | 公开网页搜索 |
| RAG | 检索 + Prompt 生成 | 大模型回答无依据问题 | 检索质量决定答案上限 | 企业知识库问答 |
| Agentic Search | 任务规划 + 多步工具调用 | 复杂多跳问题需人工整理 | 链路过长时错误累积 | 深度调研、代码助手 |
| 向量语义搜索 | Embedding + 相似度计算 | 词汇不一致导致漏检 | 精确匹配与过滤较弱 | 语义召回、推荐 |
| 图结构搜索 | 知识图谱 + 路径遍历 | 实体关系多维查询 | 构建图谱成本高 | 金融风控、医疗知识 |
从趋势上看,主流“新类型”搜索引擎大概率不是单一路线的完全胜利,而是以 Agentic Search 为交互框架,以 RAG 为底料,混合使用向量检索与关键词检索的复合架构。
4. 从“检索”到“答案生成”:核心范式变化
接下来从架构角度,梳理一下“新类型搜索”到底把哪些环节的权重移走了。
第一,从“查全率优先”转向“答案正确性优先”。传统搜索引擎为了不遗漏用户可能想看的内容,倾向于尽可能多地覆盖结果。而新型搜索因为要走“生成-引用”流程,宁愿少召回到无关内容,也不希望把噪声片段注入生成器,导致答案偏离事实。
第二,从“一次请求”转向“多轮规划”。传统搜索的无状态特性决定了每个查询之间相互独立。Agentic Search 则把用户的查询视为一个任务的起点,搜索系统内部自主决定下一步“还要查什么”。这意味着搜索系统开始具备像人一样的探索行为——这在旧架构中是根本不存在的概念。
第三,从“页面列表”转向“答案+证据”。新型搜索的输出不再是一串链接,而是一个完整的回答段落,但每个关键句后面都标注了信息来源。这就要求系统内部具备“答案段落 -> 引用文档 -> 原文句子”的可追溯链条。这在工程上是一个不小的挑战,因为我们不能只生成一个好看的答案,还必须保证答案中的每个事实性论断都能在源文档中找到对应依据。
第四,从“静态排序公式”转向“动态推理系统”。传统搜索引擎中,排序由一个固定的打分公式完成;新型搜索中,结果的相关性由生成模型在理解完整上下文后隐式判断。这带来了一个工程上的巨大差异:传统搜索的排序是可调试、可解释、可评测的,而基于 LLM 的排序则更接近黑盒,评测与回归控制会更难。
这四点变化,决定了新型搜索的工程实现路径与老一代搜索完全不同:我们不再只建索引,而是需要构建数据管线、Rerank 服务、Prompt 编排层和评测集。
5. 动手实现一个最小“新型搜索”原型
概念讲完了,接下来是动手环节。我们抛开复杂的 Agentic 框架,先从最小可用的语义搜索原型开始。这个原型会实现“新类型搜索”中最核心的两个能力:语义召回 + 生成式答案组装。它不依赖任何重型框架,直接用 Python 标准库加开源模型实现。
5.1 环境准备与依赖
建议使用 Python 3.10+,并准备一个虚拟环境。本示例不依赖高配 GPU,纯 CPU 环境即可运行。需要安装以下依赖:
pip install sentence-transformers flask chromadbsentence-transformers:负责把文本转成向量;chromadb:轻量级向量数据库,用于存储与检索;flask:提供本地 Web 搜索服务接口。
如果无法安装chromadb,也可以用numpy手动实现余弦相似度,文本量不大时完全够用。这里先按chromadb的标准 API 来写。
5.2 构建知识库并写入向量数据库
新建文件build_kb.py,代码如下:
# 文件路径:build_kb.py from sentence_transformers import SentenceTransformer import chromadb from chromadb.config import Settings # 初始化 embedding 模型 # 该模型是轻量级多语言模型,适合中文场景 model = SentenceTransformer('paraphrase-multilingual-MiniLM-L12-v2') # 创建本地持久化向量数据库 client = chromadb.PersistentClient(path="./kb_store") # 创建集合,metadata 可选 collection = client.get_or_create_collection( name="tech_search", metadata={"hnsw:space": "cosine"} ) # 构造知识库内容:模拟企业知识库中的 FAQ 和文档段落 documents = [ "数据库连接池的作用是复用数据库连接,避免频繁建立和关闭连接带来的性能开销。", "在 Spring Boot 中,可以通过 HikariCP 默认连接池配置数据库连接池参数。", "Redis 是一个基于内存的高性能键值存储系统,通常用于缓存和消息队列。", "RAG 检索增强生成流程包含索引构建、检索召回、重排和生成四个核心阶段。", "向量数据库通过 embedding 模型将文本转换为高维向量,并基于向量相似度检索。", "Agentic Search 的核心是让 AI 自主规划多步检索任务,并在多轮检索中积累证据。", "API 网关是微服务架构中统一入口,负责请求转发、认证鉴权和流量控制。", "JWT 令牌由 Header、Payload 和 Signature 三部分组成,适合无状态认证场景。" ] ids = [f"doc_{i}" for i in range(len(documents))] metadatas = [{"source": "internal_wiki", "index": i} for i in range(len(documents))] # 先计算向量再写入 embeddings = model.encode(documents).tolist() collection.add( ids=ids, documents=documents, metadatas=metadatas, embeddings=embeddings ) print("知识库构建完成,共写入", len(documents), "条文档")运行方式:
python build_kb.py这一步做了三件事:加载 embedding 模型、把 8 条测试文档向量化、写入本地向量数据库。
这里容易踩坑的地方是:paraphrase-multilingual-MiniLM-L12-v2第一次运行时会自动从 Hugging Face 下载模型权重,如果网络不通,推荐手动下载后放到本地模型目录,再修改模型路径。
5.3 实现语义检索接口
新建文件search_api.py,提供两个能力:一个是纯语义检索,另一个是带生成的答案组装。
# 文件路径:search_api.py from flask import Flask, request, jsonify from sentence_transformers import SentenceTransformer import chromadb app = Flask(__name__) # 加载模型与向量库 model = SentenceTransformer('paraphrase-multilingual-MiniLM-L12-v2') client = chromadb.PersistentClient(path="./kb_store") collection = client.get_collection("tech_search") @app.post("/api/search") def search(): data = request.get_json() query = data.get("query", "") if not query: return jsonify({"error": "query 不能为空"}), 400 query_embedding = model.encode([query]).tolist() # 从向量库中召回 Top 3 results = collection.query( query_embeddings=query_embedding, n_results=3, include=["documents", "distances", "metadatas"] ) # 组装响应结果 docs = results["documents"][0] distances = results["distances"][0] metas = results["metadatas"][0] matched = [] for doc, dist, meta in zip(docs, distances, metas): matched.append({ "text": doc, "score": round(float(dist), 4), "source": meta.get("source", "unknown"), "index": meta.get("index", -1) }) return jsonify({"query": query, "results": matched}) @app.post("/api/answer") def answer(): """ 在语义检索基础上,模拟简单的生成式答案组装。 实际生产环境可替换为 LLM 调用。 """ data = request.get_json() query = data.get("query", "") if not query: return jsonify({"error": "query 不能为空"}), 400 query_embedding = model.encode([query]).tolist() results = collection.query( query_embeddings=query_embedding, n_results=2, include=["documents", "distances"] ) docs = results["documents"][0] # 简易答案组装:把检索到的片段拼成带引用的上下文 context = "\n".join([f"- {doc}" for doc in docs]) answer_text = f"根据检索到的资料,相关内容如下:\n{context}" return jsonify({ "query": query, "answer": answer_text, "sources": docs }) if __name__ == "__main__": app.run(host="0.0.0.0", port=8000)运行服务:
python search_api.py代码要点说明:
chromadb.PersistentClient(path="./kb_store")读取的是上一步构建好的向量库;include参数控制返回内容,这里同时返回原文、距离分数和元数据;- 这个 API 已经具备了一个“新型搜索引擎”的最小雏形:输入自然语言,首先做语义召回,然后基于召回结果组装答案。
注意:这个示例的/api/answer还只是把检索片段拼接起来,不是真正意义上的 LLM 生成。生产环境中,这一步应该替换为大语言模型的 Prompt 调用,把docs作为上下文传入,让模型基于上下文整理答案。
5.4 用 curl 验证效果
启动服务后,打开一个新终端,执行:
curl -X POST http://localhost:8000/api/search \ -H "Content-Type: application/json" \ -d '{"query": "数据库连接有哪些优化方式"}'预期返回效果(片段示例):
{ "query": "数据库连接有哪些优化方式", "results": [ { "text": "数据库连接池的作用是复用数据库连接,避免频繁建立和关闭连接带来的性能开销。", "score": 0.6342, "source": "internal_wiki", "index": 0 }, ... ] }再测试一下“关键词不一致但语义一致”的场景:
curl -X POST http://localhost:8000/api/search \ -H "Content-Type: application/json" \ -d '{"query": "如何减少频繁建立MySQL连接的开销"}'传统关键词搜索很难命中“数据库连接池”,但向量检索可以稳定召回第一条文档。在这个最小示例里,你已经体验到了“新类型搜索”和传统搜索的第一个核心差异:语义匹配。
6. 如何验证搜索结果质量
写完了代码,一个更实际的问题是:怎么知道这套搜索好不好用?这里介绍三个面向工程研发的验证手段。
第一,人工相关性评估集(Golden Set)。准备 20 到 50 组“问题-期望命中文档”对,每次改动检索策略后,计算 Top K 命中率。这是最简单、最可靠的回归手段。计算公式:
- Recall@K = 在返回的前 K 条结果中,命中期盼文档的数量 / 期望文档总数;
- MRR(Mean Reciprocal Rank)= 第一条命中期盼文档的位置的倒数的平均值。
第二,端到端答案质量评估。把搜索系统接到大模型上后,不能只看召回率,还要看最终答案的质量。可以人工评估三个维度:
- 引用来源是否真实支撑了答案;
- 是否遗漏了核心论据;
- 有没有为了通顺而引入上下文之外的幻觉信息。
第三,A/B 对比测试。这需要比较完善的数据埋点,适合产品上线后使用。观察用户点击率、会话长度、答案点赞/踩的反馈率等指标。
在新类型搜索引擎开发中,最常见的误区是:过度关注 Embedding 模型的效果,而忽视数据清洗和分块策略。我见过不少项目,花了很多时间在找“最好的向量模型”上,结果最后发现问题是文档切得太碎,导致关键上下文被截断,怎么换模型都拉不回来。搜索系统的性能瓶颈,很多时候不在模型,而在数据工程。
7. 常见问题与排查方法
结合上述最小原型和行业常见实践,整理一张问题排查表,按出现频率排序:
| 问题现象 | 可能原因 | 排查方式 | 解决方案 |
|---|---|---|---|
| 搜索结果与查询语义完全不相关 | Embedding 模型与文档语言不匹配 | 换一个同语言优化的模型,测试多条相似 query | 使用多语言模型或领域微调模型 |
向量库查询报Collection not found | 先执行了搜索脚本,但没有先构建知识库 | 检查kb_store目录 | 先运行build_kb.py再启动搜索服务 |
| 检索结果都是同一条文档,多样性差 | 知识库数据量太少,或文档间语义太相似 | 打印召回文档的documents列表 | 增加数据量,并调整n_results |
| 启动时加载模型很慢 | 模型较大,或首次下载权重文件 | 观察日志确认是在下载还是加载 | 使用轻量模型如all-MiniLM-L6-v2 |
| 相似度分数普遍偏低 | 嵌入空间分布稀疏,或 query 过长 | 检查 query 文本长度,尝试缩短查询 | 先用 LLM 做查询改写,再走检索 |
| 生产环境中文检索效果差 | 分句方式可能切断了语义单元 | 检查分块策略,观察切块长度 | 按段落或语义边界分块,避免固定字符截断 |
这里特别提示一点:在向量数据库选型上不必急于引入重型组件。原型阶段用chromadb、faiss这种轻量方案完全够用;等到数据量达到百万级、并发量上来了,再考虑Milvus、Elasticsearch内置向量检索等高并发方案。过早引入分布式检索系统,只会让项目前期迭代速度变慢。
8. 工程落地:从 Demo 到生产环境的五个建议
如果看完上面这些,你决定在自己项目中试用“新型搜索”技术,下面是五个比较重要的工程建议。
第一,先做数据分块和清洗,再选模型。数据分块的大小会直接影响检索效果。太短丢上下文,太长噪声大。经验值,中文场景下 200 到 500 字一个分块比较合理,但必须结合具体文档结构调整。建议保留章节标题作为上下文前缀。
第二,不要只依赖向量检索,混合检索是底线。生产环境必须同时跑关键词检索(BM25)和向量检索,然后用 Reranker 做融合。原因很简单:向量检索不擅长精确匹配,比如产品型号“A100-80G”,BM25 能精确命中,向量可能因为语义距离偏转而漏掉。
第三,答案必须强制引用来源。你可以在 Prompt 里强制要求模型只能基于context回答,并要求在答案末尾列出引用片段编号。没有引用来源的“新类型搜索”就失去了相对于传统搜索的信任优势。这在企业知识库场景下尤其重要。
第四,建立“查询改写”环节。用户输入常常是口语化的、有歧义的,比如直接输入“mysql 连不上”。我们可以用一个小模型做意图分类和实体抽取,把“mysql 连不上”改写为“MySQL 数据库连接失败 错误排查”,然后再进入检索。这个前置步骤能在不大幅增加延迟的情况下显著提升检索质量。
第五,做好链路监控和失败降级。新搜索链路中,Embedding 服务的延迟、Reranker 的超时、LLM 的调用失败,任何一个环节出问题都会导致整个搜索不可用。因此需要在架构中预留降级方案:比如 LLM 不可用时,直接返回纯检索列表,而不是返回空白失败页。
9. 未来方向:新型搜索引擎会取代传统搜索吗
回到文章开头的问题:这类“Show HN: A new type of search engine”会不会彻底改变搜索市场?
比较稳妥的判断是:短期内它不会取代传统搜索,但会重新划分搜索场景。
在简单事实查询、热点新闻检索、小众页面导航这些场景中,传统搜索的效率和成本优势依然显著。但在企业知识库问答、专业调研、代码检索、客服问答这些“高信息消化成本”的场景中,新的搜索范式会逐渐占据主导,这是一个确定性的趋势。
从技术演进角度看,下一代搜索的核心议题已经不再是“如何构建更大规模的索引”,而是以下三个方向:
- 如何让 AI 更准确地判断“什么时候该停止检索并开始总结”;
- 如何让多轮检索过程中的证据链可追溯、可审计;
- 如何在答案生成中融合私有数据与公开数据,同时控制隐私边界。
这些问题的解决,依赖的是更成熟的 Agentic 框架、更强的评测体系,以及更可信的引用机制。对于开发者来说,现在正是入局的好时机——与其等平台级产品定型,不如先用开源组件跑通一条自己的语义搜索链路,积累工程经验。
如果你要动手实践,建议从本文第 5 节的最小原型开始,先替换成你自己领域的数据,然后逐步加入查询改写、混合检索、Reranker、LLM 生成这几层能力。每一步在你自己的数据集上做评测,你会比看任何评测报告都更清楚“新类型搜索”的边界在哪里。今天的分享就到这里,代码可以直接复制保存,建议收藏备用。