一个 std::vector 可以被赋值给另一个 std::vector 吗?

5

假设我有以下内容:

std::vector<int> myints;

今日免费次数已满, 请开通会员/明日再来
std::vector<int> GiveNumbers()
{
  std::vector<int> numbers;
for(int i = 0; i < 50; ++i)
{
  numbers.push_back(i);
}

return numbers;
}

我能这样做吗:

myints = GiveNumbers();

做这个操作安全吗?这样做会使myints数组只包含0到49的数字,没有其他内容吗?这样做会清空之前可能存在于myints中的内容吗?如果不是,请问正确的操作方式是什么?
谢谢。
4个回答

7

是的,这是安全的。你将会从你的GiveNumbers()函数中复制结果到myints。这可能不是最有效的方法,但它是安全且正确的。对于小向量,效率差异不会很大。


2
如果您的编译器支持RVO,那么它不应该是低效的。 - jamesdlin
1
RVO应该只将复制减少到一次。 - James Curran

1

正如已经提到的,这种方法是完全安全的,尽管不是最有效的方法。

为了节省资源,最好通过引用传递您的向量,并直接修改它。

void setNumbers(vector<int> &nums)
{
   nums.resize(50);
   for(int i = 0; i < 50; ++i)
   {
      nums[i] = i;
   }
}

正如之前提到的,对于非常小的向量,效率可能没有太大的差别,但对于较大的向量,实际上可以节省很多时间。

通过直接修改原始向量,您获得的节省有两种方式:

  1. 内存节省(不创建临时向量)
  2. 速度节省(只需迭代N次即可一次性设置向量,而不是进行第一次设置临时向量和第二次将其复制到原始向量中的操作)

如果您的编译器支持RVO,它会为您执行该转换,因此不应该效率低下。 - jamesdlin
此外,您的版本应该注意使用引用参数时,首先调用std::vector::clear()或检查传入的参数是否超过50个元素。 - jamesdlin
@jamesdlin:请注意nums.resize(50);的使用。 - KevenK
哎呀,你说得对。我不知道为什么会忘记 resize 可以缩小。傻啊。也许我在想 reserve - jamesdlin
@jamesdlin:我非常怀疑RVO能够给你提供这个函数所提供的所有优势。虽然它会优化掉一些临时变量,但这仍然是更有效的。 - A. Levy

1

是的,它会分配并清除之前接收向量中的内容。


1

实际上,你在 GiveNumbers() 中的 return numbers 操作会将向量复制到堆栈中。

当你使用 operator= 时,你将得到相同的内容存储到新向量中。


我为你的非常好的评论投了一票。可能由于优化,在现实生活中它不会调用op=。 - pm100

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接