2013-01-03 28 views
0

可能重複:
Why can templates only be implemented in the header file?C++多個C++文件 - LD:符號(S)沒有發現建築x86_64的

當我把我的Stack.cpp到Stack.h它的工作原理很好,但是,當我分開Stack.h,.cpp文件時,會出現此錯誤。 我還有main.cpp的文件,它不只是包括AlgebraicExpression.h 我使用這個命令編譯: 「G ++ -o主要的main.cpp AlgebraicExpression.cpp Stack.cpp」

Undefined symbols for architecture x86_64: "Stack<char>::pop()", referenced from: 
     infix2postfix(char*) in ccKgncmm.o "Stack<char>::top()", referenced from: 
     infix2postfix(char*) in ccKgncmm.o "Stack<char>::push(char)", referenced from: 
     infix2postfix(char*) in ccKgncmm.o "Stack<char>::size()", referenced from: 
     infix2postfix(char*) in ccKgncmm.o "Stack<char>::Stack()", referenced from: 
     infix2postfix(char*) in ccKgncmm.o "Stack<double>::pop()", referenced from: 
     evaluatePostfix(char*) in ccKgncmm.o "Stack<double>::top()", referenced from: 
     evaluatePostfix(char*) in ccKgncmm.o "Stack<double>::push(double)", referenced from: 
     evaluatePostfix(char*) in ccKgncmm.o "Stack<double>::Stack()", referenced from: 
     evaluatePostfix(char*) in ccKgncmm.o ld: symbol(s) not found for architecture x86_64 collect2: ld returned 1 exit status 

AlgebraicExpression.h

char* infix2postfix(char *infix); 
double evaluatePostfix(char*); 

Stack.h

#ifndef STACK_H 
#define STACK_H 

template <class T> 
class Stack 
{ 
public: 
     Stack(); 
     void pop(); 
     T top(); 
     void push(T val); 
     int size(); 

     T *values; 
     int maxSize; 
     int length; 
}; 

#endif 

AlgebraicExpression.cpp

#include "AlgebraicExpression.h" 
#include "Stack.h" 
using namespace std; 
bool isOperator(char c) 
{ 
     if(c=='+' || c=='-' || 
       c=='*' || c=='/') 
       return true; 
     return false; 
} 

bool isDigit(char c) 
{ 
     if(c=='0'||(c>='1'&&c<='9')) 
       return true; 
     return false; 
} 

int compareOperators(char c1,char c2) 
{ 
     int v1,v2; 
     if(!isOperator(c1) || !isOperator(c2)) 
       return -1; 
     if(c1 == '*' || c1 =='/')v1 = 1; 
     else v1 = 0; 
     if(c2 == '*' || c2 == '/')v2 = 1; 
     else v2 = 0; 

     return v1-v2; 
} 

char *infix2postfix(char *infix) 
{ 
     int lenIn,lenPost; 
     for(lenIn=0,lenPost=0;infix[lenIn];++lenIn) 
       if(infix[lenIn]!='('&&infix[lenIn]!=')') 
         ++lenPost; 

     char *postfix = new char[lenPost+1]; 
     int i,j; 
     Stack<char> operations; 

     for(i=0,j=0;i<lenIn&&j<lenPost;++i) 
       if(isDigit(infix[i])) 
         postfix[j++] = infix[i]; 
       else if(isOperator(infix[i])) 
       { 
         while(operations.size()&& 
           compareOperators(operations.top(),infix[i])>-1) 
         { 
           postfix[j++] = operations.top(); 
           operations.pop(); 
         } 
         operations.push(infix[i]); 
       } 
       else 
       { 
         if(infix[i] == '(') 
           operations.push(infix[i]); 
         else if(infix[i] ==')') 
         { 
           while(operations.size()&&operations.top()!='(') 
           { 
             postfix[j++] = operations.top(); 
             operations.pop(); 

           } 
           operations.pop(); 
         } 
       } 
     while(operations.size()) 
     { 
       postfix[j++] = operations.top(); 
       operations.pop(); 
     } 
     postfix[j] = '\0'; 
     return postfix; 
} 

double evaluatePostfix(char *postfix) 
{ 
     Stack<double> result; 
     for(int i=0;postfix[i];++i) 
       if(isDigit(postfix[i])) 
         result.push(postfix[i]-'0'); 
       else 
       { 
         double n1,n2,r; 
         n1 = result.top(); 
         result.pop(); 
         n2 = result.top(); 
         result.pop(); 
         if(postfix[i] == '+') 
           r = n1+n2; 
         else if(postfix[i] == '-') 
           r = n2-n1; 
         else if(postfix[i] == '*') 
           r = n1*n2; 
         else if(postfix[i] == '/') 
           r = n1/n2; 
         result.push(r); 
       } 
     return result.top(); 
} 

Stack.cpp

#include "Stack.h" 
template <class T> 
Stack<T>::Stack() 
{ 
     maxSize = 100; 
     length =0; 
     values = new T[maxSize]; 
} 

template <class T> 
T Stack<T>::top() 
{ 
     return values[length-1]; 
} 

template <class T> 
void Stack<T>::push(T val) 
{ 
     if(maxSize==length) 
     { 
       T *temp = new T[length*2]; 
       for(int i=0;i<length;++i) 
         temp[i] = values[i]; 
       values = temp; 
       maxSize = length*2; 
     } 
     values[length++] = val; 
} 

template <class T> 
void Stack<T>::pop() 
{ 
     if(length>0) 
       length--; 
} 

template <class T> 
int Stack<T>::size() 
{ 
     return length; 
} 
+0

@billz感謝,它幫助了很多。我的代碼工作正常現在:) – mayy00

回答

2

帶班模板所有的定義需要在頭本身。

C++ FAQ是一個很好看的。

基本上當一個模板類實例化時,需要能夠看到類的定義整體,而不僅僅是標題。

如果你知道所有類是要與所使用的類型,你可以與所有這些類型的然後留在CPP定義實例化的模板,如解釋in this C++ FAQ entry

如上所述,這也包括在Why can templates only be implemented in the header file?

+1

這將是更好,如果你還可以指向http://stackoverflow.com/questions/495021/why-can-templates-only-be-implemented-in-the-header-file – abnvp

+0

感謝您的快速回復。這是我的家庭作業,老師期待我的Stack.h和Stack.cpp。反正沒有做到這一點? – mayy00

+0

@ mayy00檢查billz和我發佈的鏈接。鏈接的帖子告訴方法 – abnvp

相關問題