如何使用初始化器列表初始化包含 boost::array<> 的 Boost.Fusion 向量

How to initialize Boost.Fusion vector containing boost::array<> with initializer list

提问人:anni 提问时间:7/1/2022 最后编辑:anni 更新时间:7/1/2022 访问量:105

问:

我需要使用初始化器列表初始化一个 boost::fusion::vector,将 boost::array 作为元素。这可能吗?

boost::array<bool, 2> ary{true, false}; // works
boost::fusion::vector<int, bool> vec1{ 5, false}; // works
boost::fusion::vector<bool, std::array<bool, 2>> vec2{ false, {true, false} }; // doesn't work :(

错误:

<source>: In function 'int main()':
<source>:116:55: error: converting to 'boost::fusion::vector<int, bool>' from initializer list would use explicit constructor 'boost::fusion::vector<T>::vector(U&& ...) [with U = {int, bool}; <template-parameter-2-2> = void; T = {int, bool}]'
     boost::fusion::vector<int, bool> vec1 = { 5, false};
                                                       ^
<source>:117:81: error: no matching function for call to 'boost::fusion::vector<bool, std::array<bool, 2> >::vector(<brace-enclosed initializer list>)'
     boost::fusion::vector<bool, std::array<bool, 2>> vec2{ false, {true, false} };
                                                                                 ^
In file included from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector.hpp:12,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/include/vector.hpp:11,
                 from <source>:14:
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:302:9: note: candidate: 'template<class Sequence, class> constexpr boost::fusion::vector<T>::vector(Sequence&&)'
         vector(Sequence&& seq)
         ^~~~~~
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:302:9: note:   template argument deduction/substitution failed:
<source>:117:81: note:   candidate expects 1 argument, 2 provided
     boost::fusion::vector<bool, std::array<bool, 2>> vec2{ false, {true, false} };
                                                                                 ^
In file included from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector.hpp:12,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/include/vector.hpp:11,
                 from <source>:14:
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:289:18: note: candidate: 'template<class ... U, class> boost::fusion::vector<T>::vector(U&& ...)'
         explicit vector(U&&... u)
                  ^~~~~~
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:289:18: note:   template argument deduction/substitution failed:
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:279:35: error: mismatched argument pack lengths while expanding 'boost::is_convertible<U, T>'
                 sizeof...(U) >= 1 &&
                 ~~~~~~~~~~~~~~~~~~^~
                 fusion::detail::and_<is_convertible<U, T>...>::value &&
                 ~~~~~~             
In file included from /opt/compiler-explorer/libs/boost_1_70_0/boost/config.hpp:61,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/aux_/config/msvc.hpp:19,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/aux_/config/adl.hpp:17,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/aux_/adl_barrier.hpp:17,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/bool_fwd.hpp:17,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/bool.hpp:17,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/aux_/na.hpp:17,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/mpl/vector.hpp:19,
                 from <source>:5:
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:274:9: note: candidate: 'constexpr boost::fusion::vector<T>::vector() [with T = {bool, std::array<bool, 2>}]'
         BOOST_DEFAULTED_FUNCTION(vector(), {})
         ^~~~~~~~~~~~~~~~~~~~~~~~
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:274:9: note:   candidate expects 0 arguments, 2 provided
In file included from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector.hpp:12,
                 from /opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/include/vector.hpp:11,
                 from <source>:14:
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:262:12: note: candidate: 'constexpr boost::fusion::vector<bool, std::array<bool, 2> >::vector(const boost::fusion::vector<bool, std::array<bool, 2> >&)'
     struct vector
            ^~~~~~
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:262:12: note:   candidate expects 1 argument, 2 provided
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:262:12: note: candidate: 'constexpr boost::fusion::vector<bool, std::array<bool, 2> >::vector(boost::fusion::vector<bool, std::array<bool, 2> >&&)'
/opt/compiler-explorer/libs/boost_1_70_0/boost/fusion/container/vector/vector.hpp:262:12: note:   candidate expects 1 argument, 2 provided
<source>:115:27: warning: unused variable 'ary' [-Wunused-variable]
     boost::array<bool, 2> ary{true, false};
                           ^~~

使用 GCC 8.3,提升 1.70

感觉我缺少一些关于初始值设定项列表如何工作的基本理解。任何帮助将不胜感激。

C++ Boost-Fusion

评论

0赞 anni 7/2/2022
我意识到它适用于升压 1.53,但在升压 1.70 时失败:(这可能是 boost 库的回归吗?

答:

1赞 sehe 7/1/2022 #1

这是对推导嵌套大括号初始值设定项的语言限制。

我可以使用 C++17 CTAD 想出的最佳版本是

Live On 编译器资源管理器

#include <array>
#include <boost/fusion/include/make_vector.hpp>
#include <boost/fusion/include/vector.hpp>

int main() {
  auto vec = boost::fusion::make_vector(false, std::array{true, false});
}

评论

0赞 anni 7/2/2022
感谢您的回复!它似乎适用于 boost 1.53,但不适用于 boost 1.70,所以感觉它与 boost 库有关,而不是语言限制。
2赞 sehe 7/2/2022
这大大改变了问题,我真的帮不上忙。最有可能的变化是 Fusion 开始支持更多的东西,这使得构造函数不可推导/模棱两可。这并不是真正的倒退,更像是新功能/权衡