以下程序似乎每次都在最后崩溃,我假设这是因为一旦我到达i =(size-1),那么wordList [i + 1]将不会返回任何内容,返回null或等效的东西。有什么方法吗?我是否认为这是我问题的根源?
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <iomanip>
using std::cin;
using std::cout; using std::endl;
using std::sort;
using std::string; using std::vector;
// Obtain a list of words and return the de-duped list
// with an accompanying word count
int main()
{
cout << "Enter a series of words separated by spaces, "
"followed by end-of-file: ";
vector<string> wordList;
string x;
while (cin >> x)
wordList.push_back(x);
typedef vector<string>::size_type vec_sz;
vec_sz size = wordList.size();
if (size == 0) {
cout << endl << "This list appears empty. "
"Please try again." << endl;
return 1;
}
sort(wordList.begin(), wordList.end());
cout << "Your word count is as follows:" << endl;
int wordCount = 1;
for (int i = 0; i != size; i++) {
if (wordList[i] == wordList[i+1]) {
wordCount++;
}
else {
cout << wordList[i] << " " << wordCount << endl;
wordCount = 1;
}
}
return 0;
}
答案 0 :(得分:7)
两个问题。
首先,通常最好循环,直到你的索引为&lt;你的尺寸,而不是使用!=。你有什么应该仍然在这里工作。
问题在于这一行:
if (wordList[i] == wordList[i+1])
您需要先提前停止循环(i&lt; size - 1)或更改if语句,以便在至少再有一个条目时检查wordList [i] == wordList [i + 1]在阵列中。
更简单的方法可能是从i = 1循环到i&lt;大小,并检查wordList [i-1] == wordList [i]:
for(int i = 1; i < size; i++) {
if(wordList[i - 1] == wordList[i]) {
/* same as before */
}
/* everything else the same */
}
这将阻止您需要额外的if语句,但仍然可以保护您不会离开数组的边界。
编辑:
正如评论中所提到的,如果您使用所有原始代码并且只是像我提到的那样更改循环,则会出现一个1分之一的错误,但它很容易修复。
将单词计数开始为1而不是0.您知道您将始终至少有一个唯一单词。这个循环会在它看到一个新单词时递增该计数,所以你最终会得到正确的计数。
你需要的唯一额外处理是当wordList为空时。因此,您需要快速检查单词列表是否为空,在这种情况下,计数为0。
答案 1 :(得分:3)
您需要进行两项更改。如前面的评论中所述,您的结束条件应为&lt; size-1以防止读出界限。你还需要打印最后一项的计数,这将是wordCount,因为如果它的唯一wordCount是1,如果没有,它已经被添加。更正后的代码:
for (int i = 0; i < size-1; i++) {
if (wordList[i] == wordList[i+1]) {
wordCount++;
}
else {
cout << wordList[i] << " " << wordCount << endl;
wordCount = 1;
}
}
cout << wordList[size-1] << " " << wordCount << endl;
答案 2 :(得分:2)
您应该将代码更改为for (int i = 0; i < size-1; i++) {
,因为wordList[i+1]
i+1
的值必须小于size
。结果意味着i < size -1
。
C / C ++数组是否可以包含从0
到size-1
的索引。
答案 3 :(得分:1)
是。边界条件失败。 vector[size()]
是未定义的值。
if (wordList[i] == wordList[i+1]) ---> out of bounds
可以循环使用size()-1
答案 4 :(得分:0)
这正是问题所在。您的向量包含“大小”项,但您尝试访问向量的末尾。
你需要做的是在最后一项之前停止for循环,这样i + 1才能访问最后一项。
例如:
for (int i = 0; i < (size - 1); i++) {
答案 5 :(得分:0)
更改
for (int i = 0; i != size; i++) {
到
for (int i = 0; i != size-1; i++) {
答案 6 :(得分:0)
那是因为对于i == size-1,i + 1 == size。并且wordList [size]不在列表的末尾。您可能需要将for循环条件更改为“i&lt; size - 1”。
答案 7 :(得分:0)
它不是NULL,它超出了范围。你应该至少检查一下我是不是在进行比较之前的大小。
我不确定你在比较中想要做什么,但这是一个更广泛的问题。
答案 8 :(得分:0)
您可以检查i == wordList长度并退出/跳过if。
答案 9 :(得分:0)
有时只是代码可以更简单......如果您使用其他东西。
问题陈述:向每个单词返回一个带有关联的单词的已删除列表。
我个人会为std :: map寻找这样的声明。
// Yeah it feels stupid, but I want default construction to initialize...
struct MyCount
{
MyCount() : _count(0) {}
size_t _count;
};
std::ostream& operator<<(std::ostream& out, const MyCount& rhs)
{
return out << rhs._count;
}
int main()
{
cout << "Enter a series of words separated by spaces, "
"followed by end-of-file: ";
typedef std::map<std::string, MyCount> map_type;
map_type wordList;
std::string x;
while (std::cin >> x)
wordList[x] += 1; // This is why I have a struct instead of a plain size_t
if (wordList.empty()) {
cout << endl << "This list appears empty. "
"Please try again." << endl;
return 1;
}
cout << "Your word count is as follows:" << endl;
for (map_type::const_iterator it = wordList.begin(), end = wordList.end(); it != end; ++ it) {
std::cout << it->first << " " << it->second << std::endl;
}
return 0;
}
我知道std :: vector是默认容器,但是如果你要“关联”两个实体(这里是一个单词及其出现次数),那么你最好不要考虑关联容器。
答案 10 :(得分:-1)
您可能想尝试
for (int i = 0; i < size; i++)
这将阻止循环尝试寻址超出范围的索引。