我写了一个模板,只有在struct
,class
重载bool operator==
时才会有效使用,否则会出现编译错误,
namespace atn {
template <typename T>
bool find( std::vector<T>& cont, T find ) {
for( std::vector<T>::iterator it = cont.begin(); it != cont.end(); ++it ) {
if( (*it) == find )
return true;
}
return false;
}
};
很好,没关系,例如:
struct sPlayer {
u_int idPlayer;
sPlayer() : idPlayer(0) {};
bool operator==( const sPlayer& ref ) const {
return ref.idPlayer == this->idPlayer;
};
};
int _tmain(int argc, _TCHAR* argv[]) {
std::vector<sPlayer>a;
sPlayer player;
player.idPlayer = 5;
a.push_back(player);
if(atn::find(a, player)){
std::cout << "Found" << std::endl;
}
return 0;
}
问题是,如果我这样使用它:
vector<int>hold;
if(atn::find(hold, 4))
我迷失在这一部分,模板假定在vector<T>
分配的T的类型是否传递了第二个参数的值?或者它将从传递的向量引用的类型中假设?
答案 0 :(得分:2)
两个论点必须匹配。模板参数推导尝试为每个模板参数找到一个类型,使函数参数类型与提供的参数的类型相匹配。
有时这会有点棘手,应该工作的事情不会。例如:
std::vector<int> v;
atn::find(v, 1U);
这失败了,因为第一个参数想要推导T = int
,但第二个参数想要T = unsigned int
。推论失败,代码无法编译。 (如果这是一个问题,那么解决方案是使除了一个函数参数非推导之外的所有函数。)
答案 1 :(得分:2)
模板假定传递的第二个参数的值在向量处分配的T的类型?或者它将从传递的向量引用的类型中假设?
都不是。编译器将分别推断每个参数的类型,然后它将验证所有情况的推断类型是否相同。如果所有参数的推断类型不相同,则无法编译。
一个常见的例子是std::max
(或std::min
)模板:
template <typename T>
T min( T lhs, T rhs ) {
return (lhs < rhs? lhs : rhs);
}
int main() {
min(1,1u); // error
}