《小S的倒排索引问题解析》 题目: 小S的倒排索引 问题描述 小S正在帮助她的朋友们建立一个搜索引擎。为了让用户能够更快地找到他们感兴趣的帖子,小S决定使用倒排索引。倒排索引的工作原理是:每个单词都会关联一个帖子ID的列表,这些帖子包含该单词,且ID按从小到大的顺序排列。 例如,单词“夏天”可能出现在帖子1、帖子3和帖子7中,那么这个单词的倒排链就是 [1, 3, 7]。如果用户想同时找到包含“夏天”和“海滩”的帖子,小S需要找出两个倒排链的交集,且将结果按照从大到小的顺序输出。现在,给定两个单词的倒排链数组 a 和 b,请你帮助小S找出同时包含这两个单词的帖子ID,并按从大到小的顺序返回结果。 测试样例 样例1: 输入:a = [1, 2, 3, 7], b = [2, 5, 7] 输出:[7, 2] 样例2: 输入:a = [1, 4, 8, 10], b = [2, 4, 8, 10] 输出:[10, 8, 4] 样例3: 输入:a = [3, 5, 9], b = [1, 4, 6] 输出:[] 样例4: 输入:a = [1, 2, 3], b = [1, 2, 3] 输出:[3, 2, 1] 解题代码: #include #include #include using namespace std;
vector solution(vector& a, vector& b) { // 初始化结果列表 vector result; // 使用双指针法查找交集 int i = 0, j = 0; while (i < a.size() && j < b.size()) { if (a[i] == b[j]) { // 找到交集元素,添加到结果列表 result.push_back(a[i]); i++; j++; } else if (a[i] < b[j]) { i++; } else { j++; } } // 对结果列表进行排序并反转 sort(result.begin(), result.end()); reverse(result.begin(), result.end()); return result; }
int main() { vector a1 = {1, 2, 3, 7}; vector b1 = {2, 5, 7}; vector res1 = solution(a1, b1); cout << (res1 == vector{7, 2}) << endl;
vector a2 = {1, 4, 8, 10}; vector b2 = {2, 4, 8, 10}; vector res2 = solution(a2, b2); cout << (res2 == vector{10, 8, 4}) << endl;
vector a3 = {3, 5, 9}; vector b3 = {1, 4, 6}; vector res3 = solution(a3, b3); cout << (res3 == vector{}) << endl;
vector a4 = {1, 2, 3}; vector b4 = {1, 2, 3}; vector res4 = solution(a4, b4); cout << (res4 == vector{3, 2, 1}) << endl;
return 0; }
一、解题思路
本题的核心任务是根据给定的两个单词的倒排链数组(即包含特定单词的帖子ID数组),找出同时包含这两个单词的帖子ID,并按照从大到小的顺序返回结果。整体思路采用双指针法来高效地找出两个数组的交集元素,然后再对交集结果进行排序和反转操作以满足输出要求。
二、代码详解
2. 初始化结果列表: vector result; 首先创建一个空的 vector 容器 result ,用于存储最终找到的同时包含两个单词的帖子ID。 3. 双指针法查找交集: int i = 0, j = 0; while (i < a.size() && j < b.size()) { if (a[i] == b[j]) { result.push_back(a[i]); i++; j++; } else if (a[i] < b[j]) { i++; } else { j++; } } 这里使用双指针 i 和 j 分别遍历数组 a 和 b 。当 a[i] 和 b[j] 相等时,说明找到了一个同时包含在两个倒排链中的帖子ID,将其添加到 result 中,然后两个指针同时后移。如果 a[i] < b[j] ,则说明 a 数组中的当前元素较小, i 指针后移;反之, j 指针后移。通过这样的比较和移动,能够高效地找出两个数组的交集元素。 4. 对结果列表进行排序并反转:sort(result.begin(), result.end()); reverse(result.begin(), result.end()); 先使用 sort 函数对 result 数组按照从小到大的顺序进行排序,这是因为后续要按照从大到小的顺序输出,所以先排好序方便后续操作。然后再使用 reverse 函数将排好序的数组反转,从而实现按照从大到小的顺序排列结果。 5. 返回结果:return result;最后将处理好的 result 数组返回,即为所求的同时包含两个单词的帖子ID列表,并按照从大到小的顺序排列。 三、总结知识点 1. 双指针技巧:双指针法在处理两个有序数组的交集、合并等问题时非常有效。通过合理移动指针,可以避免多层嵌套循环,降低时间复杂度,提高算法效率。在本题中,通过双指针高效地找出了两个倒排链数组的交集元素。 2. vector容器操作:熟练掌握 vector 容器的基本操作,如创建、添加元素( push_back )、遍历等。在本题中, vector 被用于存储帖子ID,是处理数据的重要容器。 3. 算法库函数使用: sort 和 reverse 函数来自 库, sort 用于对数组进行排序, reverse 用于反转数组。了解这些常用算法库函数的功能和使用方法,可以快速实现一些常见的算法需求,简化代码编写过程。 4. 倒排索引概念理解:本题基于倒排索引的背景,通过实际操作加深了对倒排索引原理的理解,即每个单词关联包含该单词的帖子ID列表,在搜索引擎等应用场景中具有重要作用,有助于后续处理文本搜索、信息检索等相关问题