2013-08-23 26 views
6

Bir başlık dosyasında bir ad alanı içinde bir sınıf var. Sınıf bir şablon türü gerektirir ve sadece belirli türlerin kullanılmasını istiyorum. Aşağıda bir örnek gösterilmektedir.Ad alanı içinde özel sınıf

Dosya a.hpp

// a.hpp 
namespace a_ns { 
template<class T>  
class a { 
    // stuff 
}; 
typedef a<double> a_double; 
} // end of namespace 
// stuff 

Dosya b.hpp

// main.cpp 
#include "b.hpp" 
int main() { 
    b_ns::b my_b; // <<<--- I LIKE this! 
    a_ns::a<float> my_a_which_is_not_allowed; // <<<--- I DO NOT LIKE THIS THOUGH! D: 
} 

Yani çok gördüğünüz gibi Dosya main.cpp örneğini özlemi

// b.hpp 
#include <a.hpp> 
namespace b_ns { 
    typedef a_ns::a_double b; 
} 

, Son hedef, son kullanıcının class a tipini float yazarak türünün adı olarak bildirmesine İZİN VERMEZ. d sadece önceden tanımlanmış sınıfları typedef a<double> a_double; tarafından bildirildiği gibi belirli türlerle kullanabilir.

Bu Yukarıdaki örnek buna izin düşündüm

, ancak ben b.hpp dahil çünkü sırayla a.hpp içeren, yukarıdaki gibi bir a<float> oluşturabilir olarak, yanlış! Yani problemi görüyorsun! (umarız?)

Eğer bu mümkün ise, muhtemelen basit bir çözüm var. İşte

cevap

7

uçucu olmadığından sadece kullanmak tipi takma adları kullanmak değil muktedir olmak istiyorsanız bu sürece çalışacak

#include <type_traits> 
template <typename T> 
class X 
{ 
    T i; 
    static_assert(!std::is_same<float,T>::value,"Don't use floating point"); 
}; 



int main() 
{ 
    X<int> a; 
    //X<float> b; fails at compile time 
    return 0; 
} 

bir static_assert şekilde kullanabilirsiniz doğrudan, bir uygulama ad koyabilirsiniz a kullanıcılar kullanmamayı bilmeli:

namespace a_ns { 

namespace detail { 
    template<class T>   
    class a { 
     // stuff 
    }; 
} 

typedef detail::a<double> a_double; 
} // end of namespace 

Şimdi şeykullanabilirsiniz, ancak a doğrudan kullanmak için, sizin detail ad alanı içine kazılmak zorunda kalacak ve bu genellikle yapmak için kötü bir şey olarak kabul edilir. Eğer bir kullanıcı bunu yapmak istediğine karar verirse, zaten dertten vazgeçmekten vazgeçmişler ve onlara zarar vermelerini önlemek için ekstra önlemler almamalısınız.

+1

Aslında bundan hoşlanıyorum - programcıları yapmakta zorluk çıkarmanın bir yolu yoktur. –

+0

@ DieterLücking, Kasten kendilerini deliğe kazmak zorunda kaldıklarında, bunu önlemek konusunda çok daha az endişelenmeye başlıyorsunuz. Eğer kendilerini korkutmak istiyorlarsa, bırakın onları. Orada gerçekten onlara yardımcı olabilecek bir şey varsa, en azından şimdi ona ulaşmak için bir hacke ihtiyaç duymazlar. – chris

+0

ya da Herb Sutter'in söylediği gibi: Murphy'ye karşı savunmak, Machiavelli'ye değil – TemplateRex