C++ 映射元素上循环的范围

C++ 映射元素上循环的范围,c++,c++11,C++,C++11,考虑下面的例子config\u parser是一个类的对象,其方法variable\u map()按值返回类型为std::map的对象。第一个循环给出错误或垃圾结果,而第二个循环给出正确的结果。我错过了什么 使用GCC 6.3.1、clang 3.9.1(c++14)测试的编译器 std::vector rules=config_parser.variable_map()[“CellQRule”]; for(常量自动规则:config_parser.variable_map()[“CellQRu

考虑下面的例子
config\u parser
是一个类的对象,其方法
variable\u map()
按值返回类型为
std::map
的对象。第一个循环给出错误或垃圾结果,而第二个循环给出正确的结果。我错过了什么

使用GCC 6.3.1、clang 3.9.1(c++14)测试的编译器

std::vector rules=config_parser.variable_map()[“CellQRule”];
for(常量自动规则:config_parser.variable_map()[“CellQRule”]){

std::cout假设
config\u parser.variable\u map()
按值返回,那么对于
config\u parser.variable\u map()[“CellQRule”];
config\u parser.variable\u map()
将返回一个临时的
std::map
,然后
config\u parser.variable\u map()[“CellQRule”]
将返回属于临时
std::map
的对
std::vector
的引用

这与

{
    auto && __range = range_expression ; 
    auto __begin = begin_expr ;
    auto __end = end_expr ;
    for ( ; __begin != __end; ++__begin) { 
        range_declaration = *__begin; 
        loop_statement 

    } 
} 
注意:在完整表达式之后,临时变量将被销毁;因此在
自动&&&uuuuu range=range\u expression;
之后,
\uuuuu range
将成为悬挂引用;然后,UB


另一方面,当您使用命名变量而不是临时变量时,一切正常。

假设
config\u parser.variable\u map()
按值返回,然后对于
config\u parser.variable\u map()[“CellQRule”];
config\u parser.variable\u map()
将返回一个临时的
std::map
,然后
config_parser.variable_map()[“CellQRule”];
将返回属于临时
std::map
的对
std::vector
的引用

这与

{
    auto && __range = range_expression ; 
    auto __begin = begin_expr ;
    auto __end = end_expr ;
    for ( ; __begin != __end; ++__begin) { 
        range_declaration = *__begin; 
        loop_statement 

    } 
} 
注意:在完整表达式之后,临时变量将被销毁;因此在
自动&&&uuuuu range=range\u expression;
之后,
\uuuuu range
将成为悬挂引用;然后,UB


另一方面,当您使用命名变量而不是临时变量时,一切正常。

A将是一个良好的开端。您发布的代码没有问题。错误在别处。您确定问题不在
variable\u map()中吗
?如果不修改对象,请尝试使用
const auto&
而不是
const auto
。Does
config\u parser.variable\u map()
返回副本或引用?我不知道编译器实际上是如何从基于范围的循环构建迭代的,但是如果它接受您的表达式两次并附加
.begin()
.end()
那么
变量映射()
将被调用两次。如果返回一个副本,则
开始
结束
返回的迭代器不属于同一个
向量
。如果您打算返回表示该字符串向量的
配置解析器
的实际成员,那么您应该返回一个引用,而不是副本。如果没有,我们不知道这是否是您的意图。A将是一个良好的开端。您发布的代码没有任何错误。错误在别处。您确定问题不在
variable_map()中吗
?如果不修改对象,请尝试使用
const auto&
而不是
const auto
。Does
config\u parser.variable\u map()
返回副本或引用?我不知道编译器实际上是如何从基于范围的循环构建迭代的,但是如果它接受您的表达式两次并附加
.begin()
.end()
那么
变量映射()
将被调用两次。如果返回一个副本,则
开始
结束
返回的迭代器不属于同一个
向量
。如果您打算返回表示该字符串向量的
配置解析器
的实际成员,那么您应该返回一个引用,而不是副本。如果没有,我们不知道这是否是你的意图。
{
    auto && __range = range_expression ; 
    auto __begin = begin_expr ;
    auto __end = end_expr ;
    for ( ; __begin != __end; ++__begin) { 
        range_declaration = *__begin; 
        loop_statement 

    } 
}