#include <iostream>
#include <string>
#include <vector>
#include <map>
#include <set>
#include <memory>
#include <sstream>
#include <fstream>
#include <new>
class QueryResult;//查询结果
class TextQuery//文本查询
{
private:
std::shared_ptr<std::vector<std::string>> m_file;//文件容器指针
std::map < std::string, std::shared_ptr<std::set<std::vector<std::string>::size_type>>> wm;//关键字和行号
public:
TextQuery(std::ifstream& file);//打开文件
QueryResult query(const std::string&)const;//查询关键字
};
class QueryResult
{
private:
std::string m_keyword;//关键字
std::shared_ptr<std::vector<std::string>> m_in_file;//输入文件
std::shared_ptr<std::set<std::vector<std::string>::size_type>> m_lines;//行号
public:
QueryResult(std::string keyword, std::shared_ptr<std::vector<std::string>> in_file,
std::shared_ptr<std::set<std::vector<std::string>::size_type>> lines) :
m_keyword(keyword), m_in_file(in_file), m_lines(lines) {}
private:
friend std::ostream& print(std::ostream&, const QueryResult&);
};
TextQuery::TextQuery(std::ifstream& file) :m_file(new std::vector<std::string>)//打开文件
{
std::string text;//
while (std::getline(file, text))//从文件读取一行单词
{
m_file->push_back(text);
std::istringstream line(text);//单词分解
int n = m_file->size() - 1;//当前行号
std::string word;//单词
while (line >> word)//将行文本分解为单词
{
std::shared_ptr<std::set<std::vector<std::string>::size_type>>&lines = wm[word];//lines为关键字的值(行号)
if (!lines)//第一次遇到这个单词时,这个指针为空指针
lines.reset(new std::set<std::vector<std::string>::size_type>);//分配空间
lines->insert(n);//将行号添加到set
}
}
}
QueryResult TextQuery::query(const std::string& keyword)const
{
static std::shared_ptr<std::set<std::vector<std::string>::size_type>>
nodata(new std::set<std::vector<std::string>::size_type>);
auto loc = wm.find(keyword);
if (loc == wm.end())
return QueryResult(keyword, m_file, nodata);
else
return QueryResult(keyword, m_file, loc->second);
}
std::string make_plural(std::size_t scr, const std::string& word, const std::string& ending)
{
return (scr > 1) ? word + ending : word;
}
std::ostream& print(std::ostream& os, const QueryResult& qr)
{
os << "关键字:" << qr.m_keyword << "\t" << "出现次数:" << qr.m_lines->size() << " 次"<< '\n' << std::endl;
for (auto num : *qr.m_lines)
{
os << "行数:" << num + 1 << " " << "第" << num + 1 << "行" << '\t'
<< "这一行内容是:" << *(qr.m_in_file->begin() + num) << '\n' << std::endl;
}
return os;
}
void runQueries(std::ifstream& infile)
{
TextQuery tq(infile);
while (true)
{
std::cout << "请输入需要查询的单词:" << std::endl;
std::string str;
if (!(std::cin >> str))break;
print(std::cout, tq.query(str)) << std::endl;
}
}
int main()
{
std::ifstream ifs("E:\\转换.txt");
runQueries(ifs);
return 0;
}