繁体   English   中英

C ++使用值初始化聚合类型的std :: array

[英]C++ initialize a std::array of aggregate types with values

我想知道如何初始化结构的N元素std :: array。

例:

struct SomeStruct {
  uint32_t * const entry1;
  uint16_t * const entry2;
  uint16_t * const entry3;
};

可以通过以下方式进行初始化:

static const std::array<SomeStruct , 2> arr
{nullptr, nullptr, nullptr, nullptr, nullptr, nullptr};
// nullptr just for example, would be addresses of real variables in the project

但这并不是我真正需要的,因为以下语句在没有任何警告或其他提示的情况下也可以正常工作,因此将元素默认初始化。

static const std::array<SomeStruct , 2> arr
{nullptr, nullptr, nullptr, nullptr};

我需要的是对编译器进行全面检查,检查是否所有元素都已初始化,其语法如下所示:

static const std::array<SomeStruct , 2> arr
{{nullptr, nullptr, nullptr}, {nullptr, nullptr, nullptr}};

是否可以强制C ++检查aggragte类型的所有元素是否都已初始化?

保护你!

但这并不是我真正需要的,因为以下语句在没有任何警告或其他提示的情况下也可以正常工作,因此将元素默认初始化。

它不会保留默认初始化的元素。 cppreference关于聚合初始化 ,重点是:

如果初始化程序子句的数量少于成员数量,或者初始化程序列表完全为空,则其余成员将被值初始化。 如果引用类型的成员是这些其余成员之一,则程序格式错误。

确切的用语在C ++ 11中已更改,但没有以影响您的情况的方式发生。

因此,如果要将所有初始化为nullptr,只需使用

static const std::array<SomeStruct , 2> arr{};

如果您希望在未显式初始化任何元素时发出警告,则您没有可移植的解决方案。 编译器无法知道数组其余部分的值初始化是否是有意的。

一个非便携式解决方案:GCC具有警告标志-Wmissing-field-initializers

 warning: missing initializer for member 'SomeStruct::entry2' [-Wmissing-field-initializers] {nullptr, nullptr, nullptr, nullptr}; ^ 

您可以使用std::make_arraystatic_assert作为结果类型。 std::make_array但只是一个建议,但有一个参考实现在这里

namespace details {
  template<class> struct is_ref_wrapper : std::false_type {};
  template<class T> struct is_ref_wrapper<std::reference_wrapper<T>> : std::true_type {};

  template<class T>
  using not_ref_wrapper = std::experimental::negation<is_ref_wrapper<std::decay_t<T>>>;

  template <class D, class...> struct return_type_helper { using type = D; };
  template <class... Types>
  struct return_type_helper<void, Types...> : std::common_type<Types...> {
      static_assert(std::experimental::conjunction_v<not_ref_wrapper<Types>...>,
                    "Types cannot contain reference_wrappers when D is void");
  };

  template <class D, class... Types>
  using return_type = std::array<typename return_type_helper<D, Types...>::type,
                                 sizeof...(Types)>;
}

template < class D = void, class... Types>
constexpr details::return_type<D, Types...> make_array(Types&&... t) {
  return {std::forward<Types>(t)... };
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM