perche questo codice:SFINAE con parametri di tipo funzione o array non validi?
template<typename T>
char (&f(T[1]))[1];
template<typename T>
char (&f(...))[2];
int main() { char c[sizeof(f<void()>(0)) == 2]; }
mi aspettavo di fare SFINAE e scegliendo la seconda sovraccarico, dal momento che la sostituzione di T
in T[1]
rendimenti
void [1]()
che è un tipo non valido, naturalmente. La regolazione dei tipi di parametri (array-> puntatore) viene eseguita dopo la sostituzione dei parametri del modello in parametri di funzione e il controllo di tipi risultanti validi come 14.8.2 [temp.deduct] descrive.
Ma sia Comeau che GCC non riescono a compilare quanto sopra. Entrambi con diagnostica diversa.
Comeau dice:
"ComeauTest.c", line 2: error: array of functions is not allowed
char (&f(T[1]))[1];
GCC dice (versione 4.3.3
):
error: ISO C++ forbids zero-size array
c
Significato, GCC non manca di sostituirlo, ma sceglie il primo overload di f
, restituendo una sizeof
di 1, invece di non sostituirlo davanti come Comeau.
Quale compilatore ha ragione ed il mio codice è valido? Si prega di fare riferimento o di citare la sezione standard appropriata nella risposta. Grazie!
Aggiornamento: la norma in sé contiene un esempio nella lista a 14.8.2/2
. Non so perché ho trascurato per primo:
template <class T> int f(T[5]);
int I = f<int>(0);
int j = f<void>(0); // invalid array
Mentre l'esempio è solo informativo, mostra l'intenzione di tutti quei paragrafi misteriosi e sembra mostrare il codice di cui sopra dovrebbe funzionare e respingere la prima sovraccarico.
litb chiedendo un chiarimento degli standard è una contraddizione :) – JaredPar
ho chiesto lo stesso su usenet, ma ho postato la domanda anche qui, in modo che possa essere archiviata su SO e la gente lo troverà durante la ricerca su SO. Link a usenet: http://groups.google.com/group/comp.lang.c++.moderated/browse_thread/thread/78f8cd8cf27778e3 –
Pensavo che litb fosse lo standard ...? –