lang:cpp:preprocesseur
Ceci est une ancienne révision du document !
Utiliser les std::initializer_list (crochets) avec des macros
Le préprocesseur, comme le compilateur considère la virgule comme séparateur d'argument. Mais seul le compilateur considère les crochets {}
comme un groupe d'argument. Le préprocesseur va considérer une virgule à l'intérieur d'un groupe de crochets comme un changement d'argument. La solution consiste à définir explicitement le type et à entourer les crochets par des parenthèses : (std::list<int>{.., .., ..})
.
- cpp/preprocessor/bracket.cpp
#define STR_HELPER(x) #x #define STR(x) STR_HELPER(x) #include <list> namespace { void f(const std::list<int>&) {} } // namespace #define F(XXXX, ...) f(XXXX) int main() { std::list<int> c; f(c); f(std::list<int>{1, 2, 3, 4}); f({1, 2, 3, 4}); // Failed. Macro stops at first comma. STR(F(std::list<int>{1, 2, 3, 4})); // OK STR(F((std::list<int>{1, 2, 3, 4}))); // OK STR(F(std::list<int>({1, 2, 3, 4}))); // Failed. Macro stops at first comma. STR(F({1, 2, 3, 4})); // Failed. With double parentheses, c++ can't auto deduce std::list<std::string>. STR(F(({1, 2, 3, 4}))); }
Rendu :
- cpp/preprocessor/bracket.cpp.i
namespace std { typedef long unsigned int size_t; typedef long int ptrdiff_t; typedef decltype(nullptr) nullptr_t; } namespace std { inline namespace __cxx11 __attribute__((__abi_tag__ ("cxx11"))) { } } namespace __gnu_cxx {
On voit bien que le préprocesseur respecte les parenthèses mais pas les crochets.
Passing an initialization list to a macro Archive du 21/05/2015 le 27/08/2019
lang/cpp/preprocesseur.1594198623.txt.gz · Dernière modification : 2020/07/08 10:57 de root