考虑以下搜索结果:
行。页面被索引,它只需要查找索引表中的计数和前几个项目,因此速度是可以理解的。
现在考虑使用AND操作进行以下搜索:
这让我勾选;)搜索引擎如何能够如此快速地在巨型数据集上获得AND操作的结果?我看到以下两种方式来执行任务,两者都很糟糕:
你可以和你一起as many search phrases as you want,你仍然可以在0.5秒内得到答案!怎么样?
答案 0 :(得分:2)
Markus写的关于Google并行处理多台计算机上的查询的内容是正确的。
此外,有information retrieval种算法可以让这项工作更容易一些。这样做的经典方法是构建一个inverted index,其中包含发布列表 - 按顺序包含该术语的所有文档的每个术语列表。
当搜索具有两个术语的查询时,从概念上讲,您将为两个术语('david'和'john')中的每一个获取帖子列表,并沿着它们查找,查找两个列表中的文档。如果两个列表以相同的方式排序,则可以在O(N)中完成。当然,N仍然是巨大的,这就是为什么这将在数百台并行机器上完成的原因。
此外,可能还有其他技巧。例如,如果排名最高的文档在列表中放置得更高,那么算法可能会确定它在没有遍历整个列表的情况下找到了10个最佳结果。然后它将猜测剩余的结果数量(基于两个列表的大小)。
答案 1 :(得分:1)
我认为你是从错误的角度来解决这个问题。
Google在一台计算机上没有表/索引。相反,他们将数据集严重分配到服务器上。报告显示that as many as 1000 physical machines are involved in every single query!
凭借这种计算能力,它“简单地”(高度讽刺地使用)是确保每台机器在几分之一秒内完成工作的问题。
阅读有关Google技术和基础设施的信息非常鼓舞人心且具有高度教育性。我建议您阅读BigTable,MapReduce和Google File System。
Google提供了archive of their publications,其中包含大量有关其技术的丰富信息。 This thread on metafilter还提供了运行搜索引擎所需的大量硬件的一些见解。
答案 2 :(得分:1)
我不知道谷歌是怎么做到的,但我可以告诉你,当客户需要类似的东西时我是如何做到的:
它以倒置索引开始,如Avi所述。这只是一个表格,列出了每个文档中的每个单词,文档ID,单词以及该文档中单词相关性的分数。 (另一种方法是单独索引单词的每个外观及其位置,但在这种情况下不需要。)
从那里开始,它甚至比Avi的描述更简单 - 没有必要对每个术语进行单独搜索。标准数据库摘要操作可以在一次通过中轻松完成:
SELECT document_id, sum(score) total_score, count(score) matches FROM rev_index
WHERE word IN ('david', 'john') GROUP BY document_id HAVING matches = 2
ORDER BY total_score DESC
这将返回所有具有“大卫”和“约翰”分数的文档的ID(即,两个单词都出现),按相关性的某种近似顺序排列,无论有多少,都需要大约相同的时间执行或者你正在寻找的术语很少,因为IN
表现不会受到目标集大小的影响,并且使用简单的count
来确定所有术语是否匹配。
请注意,这种简单的方法只是将“大卫”得分和“约翰”得分加在一起,以确定整体相关性;它不接受订单/接近/等。的名称考虑在内。再一次,我确信谷歌确实将其纳入了他们的分数,但我的客户并不需要它。
答案 3 :(得分:0)
我在16位机器上做了类似于今年的事情。数据集的上限大约为110,000条记录(这是一个墓地,因此对墓葬有限制)所以我设置了一系列位图,每个位图包含128K位。
搜索“david”导致我在其中一个位图中设置相关位,以表示该记录中包含“david”字样。在第二个位图中为'john'做了同样的事情。
然后您需要做的就是两个位图中的二进制'和',结果位图会告诉您哪些记录号中包含'david'和'john'。快速扫描生成的位图可以返回与这两个术语匹配的记录列表。
这种技术虽然不适用于谷歌,所以请考虑一下我的0.02美元价值。