Searcher 模块设计
Searcher 作为上层封装,主要负责处理用户搜索请求并返回结果。它依赖于底层的正倒排索引,通过一系列步骤将自然语言查询转化为结构化的数据响应。
索引初始化
为了高效管理全局索引资源,这里采用了单例模式。在初始化阶段,获取唯一的 Index 实例并构建索引。
private: ns_index::Index* index;
public: Searcher(){}; ~Searcher(){};
public: void InitSearcher(const std::string& input) {
// 获取单例索引对象
index=ns_index::Index::GetInstance();
// 根据输入路径建立索引
index->BuildIndex(input);
LOG1(NORMAL,"建立索引成功...");
}
注意:实际项目中请修正 Getinstance 为标准的 GetInstance 命名规范。
查询处理流程
Search 函数是核心入口,包含分词、触发、合并排序和构建 JSON 四个关键步骤。
1. 分词与触发
首先使用 Jieba 工具对查询字符串进行分词。随后遍历每个词,从单例索引中获取对应的倒排列表。为了避免大小写敏感导致的问题,统一转换为小写处理。
std::vector<std::string>words;
ns_util::JiebaUtil::CutString(query,&words); // 修正拼写错误 Usutl -> Util
std::unordered_map<uint64_t,InvertedElemPrint> tokens_map;
for(std::string w:words) {
boost::to_lower(w);
ns_index::InvertedList* inverted_list=index->GetInvertedList(w);
if(inverted_list==nullptr) continue;
// 遍历倒排列表,存入哈希表
for(const auto &elem : *inverted_list){
auto &item = tokens_map[elem.doc_id];
item.doc_id = elem.doc_id;
item.weight += elem.weight;
item.words.push_back(elem.word);
}
}


