gpt4 book ai didi

c++ - 从 initializer_list 构造的麻烦

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:53:37 29 4
gpt4 key购买 nike

我有一个类应该有许多不同的构造函数重载,其中之一来自 initializer_list。不幸的是,当我使用 list-initialisation 时会自动选择它。如

class foo
{
template<typename T>
foo(T const&it);

template<typename T>
foo(std::initializer_list<T> list);
};

template<typename other>
foo bar(other const&it)
{
return {it};
}

当调用第二个构造函数时,而不是第一个。这是正确的,但违反直觉,因此很危险。我怎样才能防止这种情况发生?如果第二个构造函数专门用于 list.size()==1 的情况,我会很高兴。例如

template<typename T>
foo::foo(std::initializer_list<T> list)
: foo(list.begin(), list.size()) {}

template<typename T> // private constructor
foo::foo(const T*p, size_t n)
{
if(n==1)
foo::foo(p[0]); // this does not what I want
else {
/* ... */
}
}

我尝试从另一个构造函数中显式调用第一个构造函数。这可能吗? (代码编译,但似乎没有调用预期的构造函数或实际上任何构造函数)。我可以使这项工作的唯一方法是使用新的放置:

template<typename T>              // private constructor
foo::foo(const T*p, size_t n)
{
if(n==1)
::new(this) foo(p[0]); // seems to work
else {
/* ... */
}
}

但是,如果不是完全危险的话,这至少是不雅的。有更好的解决方案吗?请注意,尝试复制第一个构造函数的工作而不是调用它并不是一个真正有用的解决方案,因为使用 SFINAE 将有许多不同的第一个构造函数用于不同类型的参数。

最佳答案

也许您可以使用可变模板代替initializer_list
像这样的东西:

#include <type_traits>

// equivalent to std::is_same but for more type.
template <typename... Ts> struct are_same : std::false_type {};
template <typename T> struct are_same<T> : std::true_type {};
template <typename T, typename ...Ts> struct are_same<T, T, Ts...> : are_same<T, Ts...> {};

class foo
{
struct dummy_t {};
public:
template <typename...Ts, typename = typename std::enable_if<(sizeof...(Ts) > 1) && are_same<typename std::decay<Ts>::type...>::value>::type>
foo(Ts&&... args);

template<typename T>
foo(T const&it);

};

关于c++ - 从 initializer_list 构造的麻烦,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23811813/

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