c++ - compile - llvm 3.7 0
¿Hay un error de compilación expuesto por mi implementación de un rasgo de tipo is_complete? (1)
El problema parece ser con la definición de void_t
. Definirlo como
template<typename... Ts>
struct make_void { typedef void type;};
template<typename... Ts>
using void_t = typename make_void<Ts...>::type;
en su lugar produce el resultado correcto ( 10
) en ambos compiladores ( Demo ).
Creo que este es el mismo problema que se menciona en la sección 2.3 de N3911 , en el documento que propone void_t
y en el número 1558 del void_t
. Esencialmente, el estándar no estaba claro si los argumentos no utilizados en las especializaciones de plantilla de alias podrían dar como resultado una falla de sustitución o simplemente se ignorarían. La resolución del CWG, adoptada en la reunión del Comité de noviembre de 2014, aclara que la definición más corta de void_t
en la pregunta debería funcionar, y GCC 5.0 implementa la resolución.
Escribí esta plantilla de rasgos de C ++ 11 para verificar si un tipo está completo:
template <typename...>
using void_t = void;
template <typename T, typename = void>
struct is_complete : std::false_type
{};
template <typename T>
struct is_complete<T, void_t<decltype(sizeof(T))>> : std::true_type
{};
y lo probé así:
struct Complete {};
int main()
{
std::cout << is_complete<Complete>::value
<< is_complete<class Incomplete>::value
<< ''/n'';
}
Esperaba que el programa de prueba imprimiera 10
, y ese es el resultado que obtengo cuando lo compilo con clang 3.4. Sin embargo, cuando se compila con gcc 4.9, imprime 11
lugar, identificando erróneamente la class Incomplete
como completa.
No estoy seguro si mi código es correcto, pero me parece que incluso si está mal, debería comportarse igual en ambos compiladores.
Pregunta 1: ¿Es correcto mi código?
Pregunta 2: ¿He encontrado un error en uno de los compiladores?
EDITAR:
No estoy pidiendo un reemplazo para mi código. Pregunto si hay un error en gcc o clang, y si esta construcción en particular es correcta o no.