简介
本篇利用之前介绍的智能指针,关联容器,顺序容器等知识,做一个文本查询程序。该程序读取文本中的内容,然后根据输入的单词,判断该单词出现多少次,出现在哪些行,每行的句子是什么。比如我们输入elment,输出如下
1 | element occurs 112 times |
需求分析
1 我们需要实现一个TextQuery类,将文件的内容按照一行一行放入vector中,vector每个元素就是这一行的内容。
2 将每一行的内容按照单词分割,构造一个map,单词作为key,行号放入set,set作为value 。这样可以根据单词找到行号的set。
3 根据输入单词查找其出现的次数和行号,将结果作为一个类QueryResult返回。
所以当我们实现完成后其调用逻辑类似如下
1 | void runQueries(ifstream &infile) |
实现TextQuery类
1 | class QueryResult; |
TextQuery声明了基于ifstream的构造函数和一个默认构造函数,同时定义了query查询函数,将查询的结果写入QueryResult类对象。
file是一个智能指针,指向一个vector,vector保存了读取文件后每行的内容。
wm是一个map,key为文件中出现的单词,value是一个智能指针,指向该单词出现的行号set。
接下来我们声明QueryResult类
1 | class QueryResult |
QueryResult构造函数接受三个参数,分别是查询的单词,单词出现的行号set的指针,以及我们读取文件保存内容的vector的指针。
我们现实TextQuery的构造函数
1 | TextQuery::TextQuery(ifstream &infile) : file(make_shared<vector<string>>()) |
构造函数读取文件,将内容写入file中,file是一个vector指针,保存了文件中每行的内容。然后分割每行字符串,将单词和其出现的行号写入wm中。wm是一个map,key就是统计的单词,value就是set的指针,set保存了该单词出现的行号序列。
接下来我们实现query查询函数
1 | QueryResult TextQuery::query(const string &str) const |
查询函数返回QueryResult对象,根据查找结果,如果找到就返回对应的行号列表等信息,否则就返回一个空行号列表。
最后我们实现print函数,打印查询结果
1 | std::ostream &print(std::ostream &os, const QueryResult &qr) |
测试
我们新建一个文本text_query.txt,内容如下
1 | hello zack !! |
然后我们在主函数中调用之前写好的runQueries函数
1 | std::ifstream file("./config/text_query.txt"); |
程序运行后会提示我们输入单词,我们输入zack,会看到输出信息如下
1 | enter word to look for, or q to quit |
总结
这一篇demo主要是复习之前学习的智能指针和容器的知识,通过综合运用,实现了一个文本查询功能的程序。接下来的内容更精彩。
源码链接
https://gitee.com/secondtonone1/cpplearn
想系统学习更多C++知识,可点击下方链接。
C++基础