循环中的矢量迭代器不可取消引用

Vector iterator not dereferencable in for loop

本文关键字:不可取 可取消 引用 迭代器 循环      更新时间:2023-10-16

我使用一个循环来计算一个单词输入了多少次,然后打印这个单词以及输入了多少次数,这很有效,但它从不打印最后一个单词,我按字母顺序排序。在打印最后一个单词之前,它会出错,说迭代器不可取消引用。这是我的循环代码:

for (vector<string>::iterator it = v.begin() ; it != v.end(); ++it)
    {
        if (*it == *(it+1))
        {
        count++;
        }
        else if (*it != *(it+1))
        {
                count++;
            cout << *it << " ---- " << count << endl;
            count=0;
        }
    }

您的代码有未定义的行为-假设it指向v的最后一个元素,那么您正试图在*(it+1) 中取消引用v.end()

if (*it != *(it+1)

STL迭代器,end不指向最后一个元素;end()返回一个迭代器,该迭代器表示容器中元素的末尾。末端是最后一个元素后面的位置。这样的迭代器也被称为过端迭代器

因此,begin()和end()定义了一个半开范围,该范围包括第一个元素,但排除最后一个

 --------------------------------
 |  |   |   |   |   |   |   |   |
 --------------------------------
  /                               /      
begin()                            end() 

对于您想要实现的目标,请查看std::adjacent_file

auto it = std::adjacent_find(v.begin(), v.end());
if (it != v.end())
{
  count ++;
}
else
{
   cout << *it << " ---- " << count << endl;
}

it == v.end() - 1时,您将(it+1)视为v.end(),而尊重CCD_ 8是未定义的行为。

当您到达最后一个单词并尝试执行时:

if (*it == *(it+1))

it+1指向v.end(),它是一个有效的迭代器,但不可撤消。因此出现了错误。

当它在结束迭代器之前时,这里有一个问题:*(it+1),因为它试图取消引用结束迭代程序,这是无效的。

我不确定在这种情况下你希望你的逻辑做什么,但你可以在做你的事情之前用if (it+1 != v.end())检查一下。

因为当it接近末尾时,it+1处于末尾,并且您试图在if运算符中取消引用它。