【问题标题】:std::map find distance with iterators, program does not terminatestd::map 使用迭代器查找距离,程序不会终止
【发布时间】:2020-03-01 20:27:45
【问题描述】:

当我编译 (g++ -std=c++14 map.cpp) 并运行这个程序时,它似乎并没有终止。任何人都可以解释为什么?然而,当我找到('a')而不是'c'时,它给出了一个零。

#include <iostream>
#include <string>
#include <vector>
#include <map> 
#include <algorithm>
using namespace std; 



int main()
{
    map<char, float> m;
    m['a'] = 3.4;
    m['b'] = 5.3;
    m['c'] = 33.3;
    m['d'] = 43.;

    auto it = m.find( 'c' );
    cout << "distance : " << std::distance( it , m.begin() ) << endl;

}

【问题讨论】:

标签: c++ iterator range distance stdmap


【解决方案1】:

使用

std::distance( m.begin(), it  )

否则调用

std::distance( it , m.begin() )

具有未定义的行为,因为使用了无效范围。 C++ 中的范围指定为[first, last ),其中第一个在最后一个之前或等于最后一个。在 first 等于 last 的最后一种情况下,范围为空。

来自 C++ 标准(27.4.3 迭代器操作)

4 效果:如果 InputIterator 满足随机访问的要求 迭代器,返回(最后 - 第一个);否则,返回的数量 从第一个到最后一个所需的增量

【讨论】:

  • 你能澄清一下为什么这是一个无效的范围吗?
【解决方案2】:

std::distance(first,last)first 开始运行并推进迭代器直到到达last。在您的情况下,这永远不会发生,因为 it 很可能在 m.begin() 之后找到,所以它会永远循环。更改给std::distance的参数顺序

std::distance参考:

如果 last 不能从 first 到达,则行为未定义 (可能重复)首先递增。

【讨论】:

  • Hm... 很可能(除非我们改为崩溃),在某些时候指针值会溢出,我们再次从空指针重新开始(当然,所有这些未定义的行为),然后最后在某个时候再次到达 begin() 迭代器。所以我们确实在某个时候停下来。如果差异类型不大于指针类型,我们甚至会由于溢出而得到所需距离的负值(好吧,再次是 UB,如果差异类型被签名)...... - 不是批评,只是提到一个有趣的问题;)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-04-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-05-27
  • 2018-04-07
  • 2012-09-13
相关资源
最近更新 更多