0

請考慮以下代碼。 A是一個抽象的泛型類; B既實現並專門化它。這段代碼對我來說看起來微不足道,但由於某種原因,我最終遇到了奇怪的鏈接器錯誤。帶有虛擬成員的模板類:鏈接器錯誤

template<typename T> 
class A { 
    public: 
     virtual void f(); 
}; 

class B : public A<int> { 
    public: 
     void f() {}; 
}; 

int main(int argc, char** argv) { 
    auto b = new B(); 
    return 0; 
} 

GCC輸出:

/tmp/ccXG2Z8A.o:(.rodata._ZTV1AIiE[_ZTV1AIiE]+0x10): undefined reference to `A<int>::foo()' 
collect2: error: ld returned 1 exit status 

鐺輸出:

/tmp/l2-2a09ab.o: In function `main': 
l2.cpp:(.text+0x35): undefined reference to `operator new(unsigned long)' 
/tmp/l2-2a09ab.o:(.rodata._ZTI1AIiE[_ZTI1AIiE]+0x0): undefined reference to `vtable for __cxxabiv1::__class_type_info' 
/tmp/l2-2a09ab.o:(.rodata._ZTI1B[_ZTI1B]+0x0): undefined reference to `vtable for __cxxabiv1::__si_class_type_info' 
/tmp/l2-2a09ab.o:(.rodata._ZTV1AIiE[_ZTV1AIiE]+0x10): undefined reference to `A<int>::foo()' 
clang: error: linker command failed with exit code 1 (use -v to see invocation) 
+1

首先A不是抽象類。你應該這樣做:virtual void foo()= 0;使其成爲一個純虛函數 – Asesh

+0

這就是它,謝謝。如果您將此作爲答案提交,我會接受它。 –

+1

你應該實現'A :: f()'或者使它成爲純虛擬的。如果缺少虛擬方法,則鏈接程序不能構建「A」的虛擬方法表。所以這個消息出現。 – Franck

回答

1

從gcc的輸出,我假設你的函數被調用foo,而不是僅僅f

問題是類A不是抽象的,因爲你還沒有聲明它的方法。你會以這種方式這樣做:

virtual void foo() = 0; 

但是你忘了= 0,因此鏈接器不知道該方法是抽象的,因此尋找一個函數體是不存在的。

1

A不是一個抽象類。你應該這樣做:

virtual void f() = 0; 

,使之成爲純虛函數