2016-05-25 11 views
5

Bardzo często w C++ klasy definicji, zwłaszcza w bibliotekach klasy cecha itp zobaczyć kod podobny do poniższego fragmentu:Dlaczego typy szablonów typename nie są domyślnie rozpoznawane jako typy?

template <typename Bar, typename Baz> 
class Foo { 
    using bar_type = Bar; 
    using baz_type = Baz; 
    // ... etc. 
} 

I tylko z tych linii można później odnieść do Foo<A,B>::bar_type lub Foo<C,D>:baz_type. Zastanawiam się: dlaczego standard językowy nie wymaga, aby kompilator automatycznie definiował typy przy użyciu parametrów szablonów typename, to znaczy pozwalał na usunięcie dwóch linii przy użyciu i rozpoznawanie Foo<A,B>::Bar jako A i Foo<C,D>::Baz jako D?

To nie powinno nawet złamać istniejącego kodu, ponieważ w Foo, bar identyfikatorów i Baz są już i tak zabrane.

+0

Ponieważ mogą nie być typami. Np. Mogą być wartością, np. N w szablonie struct array' – davidbak

+5

Nie zawsze są potrzebne, a ich ujawnienie oznacza, że ​​kod klienta może się z nimi połączyć (zakładając, że oznaczało, że te aliasy mają być jawne.) – juanchopanza

+1

Kolejna odpowiedź: ponieważ jest to łatwe do zrobienia. Jaka była odpowiedź, gdy ktoś zapytał, dlaczego nie ma słowa kluczowego "super" w C++ (ale nie mam do tego odniesienia). – davidbak

Odpowiedz

7

Nazwy parametrów nie są częścią zadeklarowanej jednostki. Dotyczy to zarówno funkcji, jak i szablonów. Poniższy kod deklaruje tylko dwa oddzielne podmioty:

extern void f(int, char, bool); 
extern void f(int a, char b, bool c); 
extern void f(int x, char b, bool z); 

template <typename> struct X; 
template <typename A> struct X; 
template <typename T> struct X; 

zwrócić szczególną uwagę, że poniższy kod jest perfekcyjnie:

template <typename T> struct X { void f(); }; // X<T>::f not yet defined 
template <typename U> void X<U>::f() {}   // now it's defined 

wszelkie próby uzyskiwania dodatkowej struktury z nazwy parametrów muszą radzić sobie z tą sytuacją. Jednym z najbardziej popularnych żądań w tym obszarze są nazwane parametry funkcji; do tej pory nie było zadowalającej propozycji takiego przedłużenia.

Do pewnego stopnia wszystkie takie propozycje wymagałyby, aby nazwy parametrów były częścią zadeklarowanej jednostki. W przypadku funkcji, na przykład, pojawi się pytanie, czy nazwy parametrów musiałyby być zmanipulowane i wystawione na działanie łącznika.

+0

Kto wie. Jedną z ukrytych implikacji nazw parametrów, które stają się częścią sygnatur funkcji, może być to, że otwierają cię one na firmy takie jak [Oracle] (https://en.wikipedia.org/wiki/Oracle_America,_Inc._v._Google,_Inc.) oskarżając cię o to. –

+0

Jestem wielokrotnie zniechęcany przez ludzi (nie wy oczywiście), którzy są w pewien sposób zirytowani pytaniami dotyczącymi tego, dlaczego status quo jest taki, jaki jest, i głosowania lub zamknięcia głosowania bez komentarza - kiedy istnieje całkowicie rozsądna odpowiedź (co potwierdza uzasadnienie na pytanie.) – einpoklum

+0

@einpoklum: Myślę, że to dobre pytanie i cieszę się, że przeczytałem pytanie i odpowiedź. Muszę jednak przyznać, że kiedy po raz pierwszy ją przeczytałem, miałem ochotę głosować, by zamknąć to, co nieuniknione, aby przepełnić stos. Powodem, dla którego myślę, że jest ta linia "Czy to było kiedykolwiek sugerowane? Dyskutowane? Odrzucono?" Nie sądzę, aby arbitralne historyczne dociekania do C++ tworzyły dobre pytania SO - pytania powinny dotyczyć programowania, a najlepiej interesującego programistę, a nie akademika czy historyka, IMO. Bez tej linii prawdopodobnie jednak będę głosował w górę. Jestem tylko jednym punktem próbnym, YMMV. –