模板类,友元运算符 <<超载
我正在尝试超载“<<”模板类的运算符。我在 .h 文件中定义了该类,并在 .cpp 文件中实现了该类。
/tmp/ccjJIJhO.o: In function `main':
main.cpp:(.text+0xad): undefined reference to `std::basic_istream<char, std::char_traits<char> >& operator>><int>(std::basic_istream<char, std::char_traits<char> >&, FeatureVector<int>&)'
main.cpp:(.text+0xba): undefined reference to `std::basic_ostream<char, std::char_traits<char> >& operator<< <int>(std::basic_ostream<char, std::char_traits<char> >&, FeatureVector<int> const&)'
collect2: ld returned 1 exit status
类定义:
common.h
#include <iostream>
using namespace std;
featurevector.h
#ifndef FEATURE_VECTOR_H
#define FEATURE_VECTOR_H
#include <common.h>
template < class FEAT_TYPE >
class FeatureVector;
template < class FEAT_TYPE >
istream & operator >> (istream &, FeatureVector<FEAT_TYPE> &);
template < class FEAT_TYPE >
ostream & operator << (ostream &, const FeatureVector<FEAT_TYPE> &);
template < class FEAT_TYPE >
class FeatureVector{
public:
FeatureVector(int = 0);
...
friend istream & operator >> <>(istream &, FeatureVector<FEAT_TYPE> & );
friend ostream & operator << <>(ostream &, const FeatureVector<FEAT_TYPE> &);
...
~FeatureVector();
private:
int m_nDim;
FEAT_TYPE * m_pFeat;
};
#endif
featurevector.cpp
#include <featurevector.h>
...
template < class FEAT_TYPE >
istream & operator >> (istream & input, FeatureVector< FEAT_TYPE> & refFeat ){
int d;
for(d=0; d < refFeat.getDim(); d++){
input >> refFeat.m_pFeat[d];
}
return (input);
}
template < class FEAT_TYPE >
ostream & operator << (ostream & output, const FeatureVector< FEAT_TYPE > & refFeat ){
int d;
for(d=0; d < refFeat.getDim(); d++){
output << refFeat.m_pFeat[d] << " ";
}
output << endl;
return (output);
}
...
#include "featurevector-impl.cpp"
featurevector-impl.cpp
template class FeatureVector<int>;
//template istream & operator >> <>(istream &, FeatureVector<int> &);
//template ostream & operator << <>(ostream &, const FeatureVector<int> &);
mylib.h
#ifndef MY_LIB_H
#define MY_LIB_H
#include <featurevector.h>
#endif
main.cpp
#include <mylib.h>
#include <common.h>
int main(){
FeatureVector<int> pFeat(10);
cin >> (pFeat);
cout << (pFeat);
return (0);
}
与 main.cpp 的“mylib”Makefile 关联的 Makefile
INC=./inc
SRC=./src
LIB=./lib
OBJ=./obj
CC=g++
CFLAGS=-O3 -Wall
mylib: $(LIB)/mylib.a
echo "mylib was created!..."
$(LIB)/mylib.a: \
$(OBJ)/featurevector.o
ar csr $(LIB)/mylib.a \
$(OBJ)/featurevector.o
$(OBJ)/featurevector.o: $(SRC)/featurevector.cpp
$(CC) -c $(CFLAGS) $(SRC)/featurevector.cpp -I$(INC) \
-o $(OBJ)/featurevector.o
clean:
rm -rf $(LIB)/*.a
rm -rf $(OBJ)/*.o
(main.cpp 及其 Makefile 位于“app”目录下)
LIB=../lib
INC=../inc
OBJ=../obj
BIN=../bin
CC=g++
CFLAGS=-O3 -Wall
LFLAGS=-lmylib -lm
[email protected]: $(LIB)/mylib.a [email protected]
cd ..; make; cd app;
$(CC) $(CFLAGS) [email protected] -o $(BIN)/$@ -I$(INC) -L$(LIB) $(LFLAGS)
clean:
rm -rf $(BIN)/*
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
根据 this,您必须在类定义中将该函数称为模板。
class.h
class.cpp
如果删除
template
行,则会出现编译错误“Underfined Reference”。According to this, you have to make the function known as template in your class definition.
class.h
class.cpp
If the line
template <typename J>
is removed, the compilation error "underfined reference" comes.请参阅常见问题解答项目 35.12 为什么我无法分离模板的定义类的声明并将其放入 .cpp 文件中?。
See FAQ item 35.12 Why can't I separate the definition of my templates class from its declaration and put it inside a .cpp file?.
您发布的错误代码表明是
operator>>
引发了未解决的外部错误,而不是operator<<
。此外,您的代码将无法编译,因为myClass
上没有采用int
的转换构造函数。所以你还没有发布正确的代码。但这有效:
Your posted error code says that it is
operator>>
that is throwing an unresolved external error, notoperator<<
. In addition, your code won't compile because there is no convert constructor onmyClass
taking anint
. So you have not posted the correct code.But this works:
别把事情搞得这么复杂:
Don't make it so complicated:
featurevector-impl.cpp 不正确。显式模板实例化如下所示:
由于运算符不是成员,因此也必须显式实例化它们:
不过,我不建议像这样拆分模板定义,除非您真的热衷于微观管理哪些特定类可以工作与您的模板(这违背了使用模板的精神)。
featurevector-impl.cpp is incorrect. Explicit template instantiations look like this:
Since the operators aren't members, they must also be explicitly instantiated:
I don't recommend splitting up your template definitions like this, though, unless you're really keen on micromanaging which specific classes will work with your template (which kind of goes against the spirit of using a template).