简体   繁体   English

宏中模板参数数量错误

[英]Wrong number of template arguments in macro

I recently upgraded from Ubuntu 16.04 to 18.04 and since then part of my C++ code doesn't compile anymore (but this could also be just coincidence). 我最近从Ubuntu 16.04升级到18.04,从那时起,我的C ++代码的一部分不再编译了(但这也可能只是巧合)。

Here a minimal example of what isn't compiling: 以下是未编译内容的最小示例:

#include <boost/test/unit_test.hpp>
#include <boost/preprocessor/punctuation/comma.hpp>
template<unsigned a, unsigned b> struct Tmpl { };
BOOST_FIXTURE_TEST_CASE( abc, Tmpl<1 BOOST_PP_COMMA() 1> ) { }

This is the error message of the gcc: 这是gcc的错误消息:

In file included from /home/ingo/opt/boost-1.68.0/include/boost/test/unit_test.hpp:19,
                 from min_ex.cpp:1:
min_ex.cpp:4:36: error: wrong number of template arguments (1, should be 2)
 BOOST_FIXTURE_TEST_CASE( abc, Tmpl<1 BOOST_PP_COMMA() 1> ) { }
                                    ^
/home/ingo/opt/boost-1.68.0/include/boost/test/unit_test_suite.hpp:142:27: note: in definition of macro ‘BOOST_FIXTURE_TEST_CASE_WITH_DECOR’
 struct test_name : public F { void test_method(); };                    \
                           ^
/home/ingo/opt/boost-1.68.0/include/boost/test/detail/pp_variadic.hpp:35:5: note: in expansion of macro ‘BOOST_TEST_INVOKE_VARIADIC’
     BOOST_TEST_INVOKE_VARIADIC(                                     \
     ^~~~~~~~~~~~~~~~~~~~~~~~~~
/home/ingo/opt/boost-1.68.0/include/boost/test/unit_test_suite.hpp:176:5: note: in expansion of macro ‘BOOST_TEST_INVOKE_IF_N_ARGS’
     BOOST_TEST_INVOKE_IF_N_ARGS( 2,                                     \
     ^~~~~~~~~~~~~~~~~~~~~~~~~~~
min_ex.cpp:4:1: note: in expansion of macro ‘BOOST_FIXTURE_TEST_CASE’
 BOOST_FIXTURE_TEST_CASE( abc, Tmpl<1 BOOST_PP_COMMA() 1> ) { }
 ^~~~~~~~~~~~~~~~~~~~~~~
min_ex.cpp:3:41: note: provided for ‘template<unsigned int a, unsigned int b> struct Tmpl’
 template<unsigned a, unsigned b> struct Tmpl { };
                                         ^~~~
In file included from /home/ingo/opt/boost-1.68.0/include/boost/test/unit_test.hpp:19,
                 from min_ex.cpp:1:
/home/ingo/opt/boost-1.68.0/include/boost/test/unit_test_suite.hpp:163:20: error: expected primary-expression before ‘)’ token
         decorators );                                                   \
                    ^
/home/ingo/opt/boost-1.68.0/include/boost/test/detail/pp_variadic.hpp:27:51: note: in expansion of macro ‘BOOST_FIXTURE_TEST_CASE_WITH_DECOR’
 #  define BOOST_TEST_INVOKE_VARIADIC( tool, ... ) tool (__VA_ARGS__)
                                                   ^~~~
/home/ingo/opt/boost-1.68.0/include/boost/test/detail/pp_variadic.hpp:35:5: note: in expansion of macro ‘BOOST_TEST_INVOKE_VARIADIC’
     BOOST_TEST_INVOKE_VARIADIC(                                     \
     ^~~~~~~~~~~~~~~~~~~~~~~~~~
/home/ingo/opt/boost-1.68.0/include/boost/preprocessor/control/iif.hpp:25:39: note: in expansion of macro ‘BOOST_PP_IIF_0’
 #    define BOOST_PP_IIF_I(bit, t, f) BOOST_PP_IIF_ ## bit(t, f)
                                       ^~~~~~~~~~~~~
/home/ingo/opt/boost-1.68.0/include/boost/preprocessor/control/iif.hpp:18:37: note: in expansion of macro ‘BOOST_PP_IIF_I’
 #    define BOOST_PP_IIF(bit, t, f) BOOST_PP_IIF_I(bit, t, f)
                                     ^~~~~~~~~~~~~~
/home/ingo/opt/boost-1.68.0/include/boost/test/detail/pp_variadic.hpp:36:9: note: in expansion of macro ‘BOOST_PP_IIF’
         BOOST_PP_IIF(                                               \
         ^~~~~~~~~~~~
/home/ingo/opt/boost-1.68.0/include/boost/test/unit_test_suite.hpp:176:5: note: in expansion of macro ‘BOOST_TEST_INVOKE_IF_N_ARGS’
     BOOST_TEST_INVOKE_IF_N_ARGS( 2,                                     \
     ^~~~~~~~~~~~~~~~~~~~~~~~~~~
min_ex.cpp:4:1: note: in expansion of macro ‘BOOST_FIXTURE_TEST_CASE’
 BOOST_FIXTURE_TEST_CASE( abc, Tmpl<1 BOOST_PP_COMMA() 1> ) { }
 ^~~~~~~~~~~~~~~~~~~~~~~

And I'm trying to compile using this command: 我正在尝试使用以下命令进行编译:

g++ -I/home/ingo/opt/boost-1.68.0/include -Wall -c -fmessage-length=0 -std=c++17 -MMD -MP -MF "min_ex.d" -MT "min_ex.o" -o "min_ex.o" "min_ex.cpp" 

I tried to find the error in the output of the preprocessor but for me it is quite hard to see anything there. 我试图在预处理器的输出中找到错误,但是对我来说很难看到任何东西。 The last two lines of the preprocessor output are: 预处理器输出的最后两行是:

template<unsigned a, unsigned b> struct Tmpl { };

struct abc : public Tmpl<1 { void test_method(); }; static void abc_invoker() { ::boost::unit_test::unit_test_log.set_checkpoint( ::boost::unit_test::const_string( "../src/test/min_ex.cpp", sizeof( "../src/test/min_ex.cpp" ) - 1 ), static_cast<std::size_t>(6), (::boost::wrap_stringstream().ref() << '"' << "abc" << "\" fixture ctor").str() ); abc t; ::boost::unit_test::unit_test_log.set_checkpoint( ::boost::unit_test::const_string( "../src/test/min_ex.cpp", sizeof( "../src/test/min_ex.cpp" ) - 1 ), static_cast<std::size_t>(6), (::boost::wrap_stringstream().ref() << '"' << "abc" << "\" fixture setup").str() ); boost::unit_test::setup_conditional(t); ::boost::unit_test::unit_test_log.set_checkpoint( ::boost::unit_test::const_string( "../src/test/min_ex.cpp", sizeof( "../src/test/min_ex.cpp" ) - 1 ), static_cast<std::size_t>(6), (::boost::wrap_stringstream().ref() << '"' << "abc" << "\" test entry").str() ); t.test_method(); ::boost::unit_test::unit_test_log.set_checkpoint( ::boost::unit_test::const_string( "../src/test/min_ex.cpp", sizeof( "../src/test/min_ex.cpp" ) - 1 ), static_cast<std::size_t>(6), (::boost::wrap_stringstream().ref() << '"' << "abc" << "\" fixture teardown").str() ); boost::unit_test::teardown_conditional(t); ::boost::unit_test::unit_test_log.set_checkpoint( ::boost::unit_test::const_string( "../src/test/min_ex.cpp", sizeof( "../src/test/min_ex.cpp" ) - 1 ), static_cast<std::size_t>(6), (::boost::wrap_stringstream().ref() << '"' << "abc" << "\" fixture dtor").str() ); } struct abc_id {}; static boost::unit_test::ut_detail::auto_test_unit_registrar abc_registrar60( boost::unit_test::make_test_case( &abc_invoker, "abc", "../src/test/min_ex.cpp", 6 ), 1> ); void abc::test_method() { }

Just try to move the template definition to an additional typedef : 只需尝试将模板定义移至其他typedef

#include <boost/test/unit_test.hpp>
template<unsigned a, unsigned b> struct Tmpl { };

typedef Tmpl<1, 1> toto;
BOOST_FIXTURE_TEST_CASE( abc, toto ) { }

The problem comes from the , that is interpreted as a macro argument. 问题来自,它被解释为宏参数。 Writing things this way is IMO much more readable that using the preprocessor library. 与使用预处理程序库相比,以这种方式编写内容使IMO更具可读性。

See this code in action here . 请参阅此处的代码。

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

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