Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/142.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/file/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 移动语义使集合迭代器无效_C++_Iterator_Move Semantics - Fatal编程技术网

C++ 移动语义使集合迭代器无效

C++ 移动语义使集合迭代器无效,c++,iterator,move-semantics,C++,Iterator,Move Semantics,我有以下不可变的容器类(公共访问值只是为了简单起见): 我使用单个容器(值为1和2)初始化容器向量。然后,我获取一个指向这个初始元素的指针并迭代每个值。对于每个值,我调用RemoveValue(),并将生成的容器插入向量中 在gcc中,这似乎效果不错。但是,我在Visual Studio 2015中遇到运行时错误 在调试模式下,错误为:“列表迭代器不可递增”。此错误发生在(int-value:currentContainer->values)的第一次迭代之后(当迭代器要递增时) 在释放模式下,错

我有以下不可变的容器类(公共访问
只是为了简单起见):

我使用单个容器(值为1和2)初始化容器向量。然后,我获取一个指向这个初始元素的指针并迭代每个值。对于每个值,我调用
RemoveValue()
,并将生成的容器插入向量中

在gcc中,这似乎效果不错。但是,我在Visual Studio 2015中遇到运行时错误

在调试模式下,错误为:“列表迭代器不可递增”。此错误发生在(int-value:currentContainer->values)的第一次迭代之后(当迭代器要递增时)

在释放模式下,错误为:“读取位置0x38处的访问冲突”。此错误发生在
RemoveValue
中的
copy.values.erase(value)
处。但仅在第二次迭代中。令人惊讶的是,
此时不再包含元素(
size()
返回0)

这两个错误我都不理解。我如何解决这些问题


也可以无错误地运行。但是,它将
2
作为容器的最终数量输出,而我预期的是三个(最初的一个,删除
1
的一个,删除
2
的一个)。

currentContainer
是指向向量
容器的元素的指针。循环体通过调用
push\u back
来修改
容器。这会使指向向量的指针无效,如果无效,
currentContainer
可能最终指向垃圾

一般来说,不要使用指向保存在
std::vector
中的对象的指针。相反,使用
containers.front()
containers[0]
获取第一个元素

struct Container
{
    std::unordered_set<int> values;

    //Default constructor
    Container() = default;

    //Copy constructor
    Container(const Container& other)
        : values(other.values)
    {   }

    //Move constructor
    Container(const Container&& other)
        : values(std::move(other.values))
    {   }

    Container RemoveValue(int value) const
    {
        //Create a copy of this object
        Container copy(*this);
        //Remove one element from the copy
        copy.values.erase(value);
        return copy;
    }
};
int main() 
{
    std::vector<Container> containers;

    {
        //Initialization
        Container initialContainer;
        initialContainer.values.insert(1);
        initialContainer.values.insert(2);

        containers.push_back(std::move(initialContainer));
    }

    const Container* currentContainer = &containers.front();
    for (int value : currentContainer->values)
    {
        Container newContainer = currentContainer->RemoveValue(value);

        //Do some checks, then...
        containers.push_back(std::move(newContainer));
    }

    std::cout << containers.size() << std::endl;

    return 0;
}