gpt4 book ai didi

c++ - std::initializer_list 无法从 推导出来

转载 作者:太空狗 更新时间:2023-10-29 20:02:48 33 4
gpt4 key购买 nike

我有一个类,其构造函数采用 initializer_list :

Foo::Foo(std::initializer_list<Bar*> bars)

如果我尝试用大括号括起来的初始化列表直接创建一个对象,initializer_list正确推导:

Foo f ({ &b }); // std::initializer_list<Bar*> correctly deduced

但是,当尝试间接 执行相同操作时(使用可变函数模板 - 在本例中为 make_unique ),编译器无法推断出 initializer_list :

std::make_unique<Foo>({ &b }); // std::initializer_list<Bar*> not deduced

错误输出:

error: no matching function for call to ‘make_unique(<brace-enclosed initializer list>)’

问题:

  • 为什么编译器无法推断出 { &b }作为initializer_list<Boo*>
  • 是否可以使用语法 std::make_unique<Foo>({ &b })我想要哪个?

完整示例如下:

#include <initializer_list>
#include <memory>

struct Bar
{};

struct Foo
{
Foo(std::initializer_list<Bar*> bars)
{ }
};

int main()
{
Bar b;

// initializer_list able to be deduced from { &b }
Foo f ({ &b });

// initializer_list not able to be deduced from { &b }
std::unique_ptr<Foo> p = std::make_unique<Foo>({ &b });

(void)f;
return 0;
}

最佳答案

make_unique 使用完美转发。

完美转发不完美有以下几个方面:

  • 转发初始化列表失败

  • 它将NULL0 转换为一个整数,然后不能将其传递给指针类型的值。

  • 它不知道它的参数是什么类型,所以你不能做需要知道它们类型的操作。例如:

    struct Foo { int x; };
    void some_funcion( Foo, Foo ) {};

    template<class...Args>
    decltype(auto) forwarding( Args&& ... args ) {
    return some_function(std::forward<Args>(args)...);
    }

    调用 some_function( {1}, {2} ) 是合法的。它使用 {1}{2} 构造 Foo

    调用 forwarding( {1}, {2} ) 不是。它在您调用 forwarding 时不知道参数将是 Foo,因此它无法构造它,也无法通过代码(因为构造列表不是变量或表达式)。

  • 如果您传递一个重载的函数名称,则无法在调用点计算出哪个重载。并且一组重载不是一个值,所以你不能完美转发它。

  • 您不能传递位域。

  • 它强制引用它的参数,即使转发的目标没有。这会以可能导致程序在技术上格式错误的方式“使用”一些静态常量数据。

  • 无法转发对未知大小数组 T(&)[] 的引用。但是,您可以调用带有 T* 的函数。

其中大约一半来自 this comp.std.c++ thread ,一旦我记得还有其他问题我想不起来了,我就开始寻找它。

关于c++ - std::initializer_list 无法从 <brace-enclosed initializer list> 推导出来,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35230920/

33 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com