c++ - 重物体的initializer_list

标签 c++ initializer-list

我有一个像这样的(模板化)函数:

template<typename T>
void func(std::initializer_list<std::vector<T>> args)
{
    for (const auto &values : inputValues)
    {
        someOperation(values);
    }
}

但我很确定这不是我想要的。我想要的是一个可以接收任意数量的 std:vector<T> 的函数避免复制(事实上,它们应该被接收为const,因为我没有在里面修改它们)。理想情况下,我希望能够传递右值和左值,例如:

std::vector<int> myVec {1, 2, 3};
func({myVec, {4, 5}});

我对当前声明的问题是,我认为(尽管我没有找到任何明确证实或反驳这一点的来源),就像现在一样,初始化列表将复制创建时的 vector (我知道在任何情况下复制初始化列表本身时它们都不会被复制);它是否正确?如果是这样的话,就是:

template<typename T>
void func(std::initializer_list<const & std::vector<T>> args)
{
    // ...
}

我在寻找什么?这允许我使用右值吗?我对与初始值设定项列表不同的选项持开放态度(我不确定是否能够使用可变参数模板,因为此函数模板是显式实例化并编译到库中的,但如果有替代方案,那会很有趣看看)。

最佳答案

您不需要 initializer_list因为如果您尝试初始化其他vector,它将强制进行复制与它同在。相反,您希望使用可变参数模板转发引用:

template<class... T>
bool func(T&&... vectors);

然后你就可以std::forward<T>(vectors)...如您认为合适。

这可以让您趁机避免复制。

例如

std::vector<int> a;
std::vector<int> b;
std::vector<int> c;
// initialize a, b, and c

func(std::move(a), std::move(b), std::move(c));

如果您想强制 const ref 接收所有 vector ,请尝试以下操作:

template<class... Vec>
bool func(const Vec&... vectors);

//...
func(a, b, c); // pass all by const ref

initializer_list在许多情况下,这是一个糟糕的选择,不仅因为构造时复制问题,还因为它引用了具有本地范围的元素数组。这里的含义是,如果您想要复制 return 它,您最终会得到静默的未定义行为(如果您意外禁用 RVO,或者编译器没有实现 RVO 或对 initializer_list 不正确地实现它,您'又不走运了)

<小时/>

重新编辑:

I am not actually using the initializer list to initialize anything, I just use it as a lightweight arguments container and, iterating its values and read the values in the vectors (I'll update the question to make that clearer). Would this also cause the creation of copies?

不,不需要创建任何拷贝。使用 initializer_list 没有问题本质上就是这样,但这不是它的预期用途。它的预期用途是让类构造函数具有 initializer_list构造函数。如果您正在寻找一个可以迭代的容器,那么创建一个引用其他 vector 的 vector 没有什么坏处(std::vector<const std::vector<int>&>)

关于c++ - 重物体的initializer_list,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45101756/

相关文章:

c++ - 为什么 C++ 允许将 std::initializer_list 强制转换为基本类型,并用于初始化它们?

c++ - 任意数量的任意类型的参数

c++ - 使用 C++11 initializer_list 实现类 std::array 容器

c++ - 引用/initializer_list 的生命周期

c++ - 为什么 "std::is_pointer<std::nullptr_t>::value"等于 false?

c++ - 为什么采用 std::initializer_list 的构造函数不首选双花括号语法

c++ - 运算符的初始化列表和 RHS

c++ - 从字符串中删除字符

java - 在 Windows App Store 之外部署的应用程序或软件中的 Microsoft Windows Advertising SDK

c++ - 对 `boost::this_thread::interruption_point()' 的 undefined reference