【问题标题】:Reading a text file and returning the word count by line in C++读取文本文件并在 C++ 中逐行返回字数
【发布时间】:2015-06-19 12:59:33
【问题描述】:

在我的编程课上,我们开始从 C 转到 C++,我们当前的实验任务是创建一个程序,它给定一个文本文件读取其内容,然后返回文件中的单词列表以及行它们出现的数量以及该单词在每行中出现的次数,格式为 Word Line:Count。

Foo bar bar
Baz
Foo
<EOF>

应该返回:

Foo  1:1 3:1
Bar  1:2
Baz  2:1

到目前为止,我们讨论的唯一数据结构是地图,我们使用地图编写了以下输出总字数的程序

int main(int argc, const char*argv[]) {
    map<string, unsigned int> table;
    string word;

    while (cin >> word) {
        ++table[word];
    }

    for (std::map<string, unsigned int>::iterator itr = table.begin();
            itr != table.end(); ++itr) {
        cout << itr->first << "\t" << itr->second << endl;
    }

    return 0;
}

我们被告知可以(稍微)最低限度地修改这个程序,以便让它打印出行号和字数。我的问题是,有没有办法使用地图为每个键设置 2 个值?或者有没有更好的方法来实现这样的东西?

【问题讨论】:

  • 1) 您必须将输入代码修改为 notice 行号,然后再担心如何存储它们,2) 每个键有 2 个值是困难的并且不足以回答,但 3)这里有一个很大的提示:而不是 map&lt;string, int&gt;,想想 map&lt;string, map&lt;int, int&gt;&gt;

标签: c++ dictionary word-count line-numbers


【解决方案1】:

您可以让您的地图将大部分内容存储为键的值。要能够计算单词出现的次数并保留它出现的行号的动态列表,您可以执行以下操作。这是我想到的最简单直接的解决方案,它不是最有效的。

使用带有字符串键值向量的map来存储,index = WordLine, value at index = Count

#include <vector>       // std::vector

using namespace std;
map<string, vector<int>> words;

当您遇到单词时,在地图中查找它们并在 line_num 索引处增加向量以表示它在该行上出现的次数。

#include <sstream>
using namespace std;

string line;
string word;
int line_num = 0;
while (getline(cin, line)) {
    istringstream words_iss(line); 
    while(line >> word) {
        ++words.at(word)[line_num];
    }
    ++line_num;
}

效率低下是因为使用索引来表示行号,因为单词可能要到第 n 行才会出现。但是,当它将它放入索引 n 处的向量时,它将为向量分配 0 - (n-1) 个整数的空间。同样在打印时,您必须检查向量中的每个值以查看它是否不为 0。

您可以通过循环遍历映射中的每个字符串,然后循环遍历每个键的向量并仅在索引处的值不为 0 时打印。

如 cmets 中所述,另一种解决方案是使用

map<string, map<int, int>> 

类似的逻辑。对于大多数情况,这会更有效。

【讨论】:

    猜你喜欢
    • 2022-01-25
    • 1970-01-01
    • 2012-10-11
    • 1970-01-01
    • 2020-09-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多