k 近邻 (k-NN) 和 近似最近邻 (ANN) 都是向量搜索中使用的算法,但它们在方法、性能和应用场景上存在显著差异。k-NN 是一种精确搜索方法,它将查询向量与数据集中的每个向量进行比较,以找到最接近的匹配项。这保证了结果的准确性,但随着数据集的增长,计算成本会变得很高。另一方面,ANN 使用近似技术来获取结果,优先考虑速度而非完美准确性。ANN 不会检查每个向量,而是将数据组织成允许跳过不相关比较的结构,使其能够扩展到大型数据集。关键区别在于权衡:k-NN 以效率为代价保证精确性,而 ANN 则牺牲部分准确性以换取更快的性能。
技术差异在于它们处理数据的方式。k-NN 计算查询向量与数据集中所有其他向量之间的精确距离(例如,欧几里得距离或余弦距离)。对于包含数百万个向量的数据集,这意味着数百万次计算,每次查询的时间复杂度为 O(n)。这对于搜索引擎等实时应用来说是不切实际的。ANN 通过将数据预处理为高效结构来避免这种情况。例如,像分层可导航小世界 (HNSW) 这样的算法构建图层以快速导航到附近的向量,而局部敏感哈希 (LSH) 则将相似的向量哈希到相同的桶中。这些方法减少了搜索空间,通常实现亚线性时间复杂度(例如,O(log n))。然而,根据配置不同,ANN 返回的邻居可能比真正的最近邻稍微远一些。例如,在产品推荐系统中,ANN 可能会优先在几毫秒内返回 95% 准确度的结果,而不是在几秒内返回 100% 准确度的结果。
选择 k-NN 还是 ANN 取决于应用程序的需求。k-NN 非常适合小型数据集(例如,少于 10,000 个向量)或当精确结果至关重要时,例如根据有限数据集验证医疗诊断。在这里,使用 scikit-learn 的 KNeighborsClassifier
等工具很容易实现。ANN 适用于图像检索或实时推荐等大规模应用。例如,拥有数百万首歌曲的音乐流媒体服务可能会使用 FAISS 或 Annoy 等 ANN 库来平衡速度和准确性。开发人员还应考虑调优:ANN 需要设置参数,例如 LSH 中的哈希函数数量或 HNSW 中的“ef”参数,这些参数控制着速度和精度之间的权衡。相比之下,k-NN 的可调参数较少,但可扩展性差。最终,选择取决于优先考虑的是准确性 (k-NN) 还是可扩展性 (ANN)。