C++primer 12.3.1节练习

练习12.27

见后面总体程序

练习12.28

 1 #include <iostream>
 2 #include <fstream>
 3 #include <sstream>
 4 #include <string>
 5 #include <vector>
 6 #include <map>
 7 #include <set>
 8 #include <cstdlib>
 9 using std::cin;
10 using std::cerr;
11 using std::cout;
12 using std::endl;
13 using std::ostream;
14 using std::ifstream;
15 using std::string;
16 using std::vector;
17 using std::map;
18 using std::set;
19 using std::istringstream;
20 
21 using line_no = vector<string>::size_type;
22 vector<string> file;            //文件每行内容
23 map<string, set<line_no>> wm;    //单词到行号set的映射
24 
25 string make_plural(size_t ctr, const string &word, const string &ending)
26 {
27     return (ctr > 1)? word + ending : word;
28 }
29 
30 string cleanup_str(const string &word)
31 {
32     string ret;
33     for (auto it = word.begin(); it != word.end(); ++it) {
34         if (!ispunct(*it))
35             ret += tolower(*it);
36     }
37     return ret;
38 }
39 
40 void input_text(ifstream &is)
41 {
42     string text;
43     while (getline(is, text)) {                //对文件中每一行
44         file.push_back(text);                //保存此行文本
45         int n = file.size() - 1;            //当前行号
46         istringstream line(text);            //将文本分解为单词
47         string word;
48         while (line>>word) {
49             // 将当前行号插入到其行号set中
50             // 如果单词不在wm中,以之为下标在wm中添加一项
51             wm[cleanup_str(word)].insert(n);
52         }
53     }
54 }
55 
56 ostream &query_and_print(const string &sought, ostream &os)
57 {
58     // 使用find而不是下标运算符来查找单词,避免将单词添加到wm中
59     auto loc = wm.find(sought);
60     if (loc == wm.end()) {                    //未找到
61         os<<sought<<" occurs 0 times"<<endl;
62     }
63     else {
64         auto lines = loc->second;            //行号set
65         os<<sought<<" occurs "<<lines.size()<<" times"<<endl;
66         for (auto num : lines)                //打印单词出现的每一行
67             os<<"\t(No "<< num+1<<"lines) "<<*(file.begin()+num)<<endl;
68     }
69     return os;
70 }
71 
72 void runQueries(ifstream &infile)
73 {
74     // infile是一个ifstream,指向我们要查询的文件
75     input_text(infile);                        //读入文本并建立查询map
76     // 与用户交互:提示用户输入要查询的单词,完成查询并打印结果
77     while (true) {
78         cout<<"enter word to look for or q to quit: ";
79         string s;
80         // 若遇到文件结尾或用户输入了q时循环终止
81         if (!(cin>>s) || s == "q") break;
82         // 指向查询并打印结果
83         query_and_print(s, cout)<<endl;
84     }
85 }
86 
87 // 程序接受唯一的命令行参数,表示文本文件名
88 int main(int argc, char **argv)
89 {
90     // 打开要查询的文件
91     ifstream infile;
92     // 打开文件失败,程序异常退出
93     if (argc < 2|| !(infile.open(argv[1]), infile)) {
94         cerr<<"No input file!"<<endl;
95         return EXIT_FAILURE;
96     }
97     runQueries(infile);
98     return 0;
99 }

练习12.29

1 do {
2      cout<<"enter word to look for ,or q to quit: ";
3      string s;
4      if (!(cin>>s) || s == "q") break;
5      query_and_print(s, cout)<<endl;
6 } while (true);

第一种,观感更好

转载于:https://www.cnblogs.com/wuyinfenghappy/p/7453098.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值