本文介绍了使用 std::vector::assign() 将向量的一部分分配给自身的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一个大小为 10 的向量(v1).现在我只想保留部分元素,使用:
v1.assign(v1.begin() + 2, v1.begin() + 6);

Let's say I have a vector(v1) of size 10. Now I want to only keep parts of the elements, using:
v1.assign(v1.begin() + 2, v1.begin() + 6);

我不确定的是,原始元素是否会在赋值之前被销毁.如果他们先被销毁,那么我不能依赖原始数据.

What I'm not sure is, whether the original elements will be destroyed before assignment. If they are destoyed first, then I cannot rely on the original data.

页面 似乎表明先删除元素.然而,一个快速的实验告诉我,数据被正确地分配给了自己.

This page seems to indicate that elements are erased first. However, a quick experiment tells me that the data are correctly assigned to itself.

那么当将向量的一部分分配给自身时会发生什么?

So what is happening when assigning part of a vector to itself ?

推荐答案

根据 C++14 标准表 100 — 序列容器要求(除了容器)

Per the C++14 standard Table 100 — Sequence container requirements (in addition tocontainer)

表达式 a.assign(i,j) 有一个前提条件,即 ij 不是 a 的迭代器.由于

The expression a.assign(i,j) has a pre-condition that i and j are not iterators into a. Since

v1.assign(v1.begin() + 2, v1.begin() + 6);

使用迭代器作为 v1 的迭代器,所以你违反了这个前提

Uses iterators that are iterators into v1 so you have violated that pre-condition

如果要重置向量以包含子范围,则可以将这些元素复制到临时向量中,然后将该临时向量分配回主向量.这应该是一个移动操作(C++11 及以上),所以不会产生额外的副本.

If you want to reset the vector to contain a subrange then you can copy those elements into a temporary vector and then assign that temporary vector back to main vector. This should be a move operation(C++11 and above) so no additional copies are made.

v = std::vector<decltype(v)::value_type>(v.begin() + 2, v.begin() + 6);

正如 Benjamin Lindley巴里 我们可以使用 std::copy移动迭代器之类的

As pointed out in the comments from Benjamin Lindley and Barry we can use std::copy and move iterators like

std::copy(std::make_move_iterator(v.begin() + 2), std::make_move_iterator(v.begin() + 6), 
          std::make_move_iterator(v.begin()));

这篇关于使用 std::vector::assign() 将向量的一部分分配给自身的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-19 13:49