2014-06-18 35 views
6

Bir polimorfik nesne üzerinde typeid kullanırken, typeid işleminin çalışma zamanı çalışma zamanında nesnenin bilgilerini alması gerektiğinden, nesnenin tanımlanması gerektiğini (yalnızca bir bildirim değil) düşünüyorum. İşte benim kod:Bir polimorfik nesnede typeid kullanıldığında, tanımlanmalı mı?

#include <iostream> 
#include <typeinfo> 

class D { 
    virtual ~D() {} 
}; 
extern D d; 

int main() 
{ 
    std::cout << typeid(d).name() << std::endl; 
    std::cout << sizeof(d) << std::endl; 
} 

Ve clang 3.4, ben bağlantı hata var: g++ 4.8.1 ile, iyi çalışıyor

undefined reference to `d'

Ama ben sonuç var:

1D
8

Benim sorum :

  1. Hangisi doğrudur?
  2. g ++ typeid'u nasıl uygular? Tanım olmadan bir polimorfik nesneden bilgiyi nasıl alabilir? clang 3.4 haklı gibi
+2

Hangisinin doğru olduğunu bilmiyorum, ancak [g ++ bağlayıcı bağlayıcısı hatası aldı] (http://coliru.stacked-crooked.com/a/288ddd8f4e70f535) extern D & d ile. Bu yüzden belki g ++ 'd' nin (D işaretçisi veya referansı değil) tip olması gerektiğini anlamaya yetecek kadar akıllıdır. –

+0

@BryanChen Ama standart tarafından izin verilmez ...? – songyuanyao

+1

Bence g ++ 'nun iyi çalışmasının sebebi de' d 'türünün olması. * Statik * 'D', bu yüzden derleyici' d' türünü bilir ve belki de g ++ çalışma zamanında '' '' typeinfo' türünü almak için en iyi duruma getirilmiş koddur. Ancak, 'd' türünün' D'' veya 'D *' olması durumunda, derleyici derleme zamanında ** türünü bilmez, bu nedenle kodu en iyi duruma getiremez. – ikh

cevap

2

http://en.cppreference.com/w/cpp/language/typeid itibaren

a) If expression is a glvalue expression that identifies an object of a polymorphic type (that is, a class that declares or inherits at least one virtual function), the typeid expression evaluates the expression and then refers to the std::type_info object that represents the dynamic type of the expression. If the result of the evaluated expression is a null pointer, an exception of type std::bad_typeid or a type derived from std::bad_typeid is thrown.

geliyor.

Güncelleme

standart diyor ki: O cppreference.com kullandığı dilden farklıdır fakat

When typeid is applied to a glvalue expression whose type is a polymorphic class type (10.3), the result refers to a std::type_info object representing the type of the most derived object (1.8) (that is, the dynamic type) to which the glvalue refers. If the glvalue expression is obtained by applying the unary * operator to a pointer and the pointer is a null pointer value (4.10), the typeid expression throws the std::bad_typeid exception (18.7.3).

hala 3.4 haklı olmak tınlamak işaret ediyor.

+0

"İfadeyi değerlendirir" ifadesi aslında standartta görünmez. – Brian

+0

Clang'ın doğru olduğuna nasıl işaret eder? – Brian

+0

@Brian, ifade bir polimorfik türden değerlendirirse, derleyicinin derleme zamanında tür bilgisini nasıl çıkarabileceğini anlayamıyorum, g ++ bazılarının nasıl çekilebildiğini bilir. –

İlgili konular