Estoy usando c ++ 17 con Boost.hana para escribir algunos programas de metaprogramación. Un problema que me atrapó es qué tipo de expresión se puede usar en un contexto constexpr como static_assert. Aquí hay un ejemplo:
#include <boost/hana.hpp>
using namespace boost::hana::literals;
template <typename T>
class X {
public:
T data;
constexpr explicit X(T x) : data(x) {}
constexpr T getData() {
return data;
}
};
int main() {
{ // test1
auto x1 = X(1_c);
static_assert(x1.data == 1_c);
static_assert(x1.getData() == 1_c);
}
{ //test2.1
auto x2 = X(boost::hana::make_tuple(1_c, 2_c));
static_assert(x2.data[0_c] == 1_c);
// static_assert(x2.getData()[0_c] == 1_c); // read of non-constexpr variable 'x2' is not allowed in a constant expression
}
{ //test2.2
auto x2 = X(boost::hana::make_tuple(1_c, 2_c));
auto data = x2.getData();
static_assert(data[0_c] == 1_c);
}
}
Primero escribo una clase X con datos de campo y un descriptor de acceso getData () . En el main () 's test1 parte, x1.data y x1.getData () se comportan igual que yo esperaba. Pero en la parte test2 , cambiar el argumento a un boost :: la tupla de hana, static_assert(x2.data[0_c] == 1_c)
todavía se comporta bien pero static_assert(x2.getData()[0_c] == 1_c)
falla la compilación, con el error de ' leer la variable no constexpr' x2 'no está permitido en una expresión constante '. Lo que es weired si divido x2.getData()[0_c]
en auto data = x2.getData();
y static_assert(data[0_c] == 1_c);
compila bien de nuevo. Esperaría que se comporten igual. Entonces, ¿alguien puede ayudar a explicar por qué x2.getData()[0_c]
no se puede usar en static_assert en este ejemplo?
Para reproducir: clang ++ 8.0 -I / ruta / a / hana-1.5.0 / include -std = c ++ 17 Test.cpp