[英]function template with stl container as an input
我收到编译错误是以下代码。 我认为这应该在c ++中起作用。有人可以帮助我了解这里的问题吗。
template < typename elem_type>
elem_type *find2( std::vector<elem_type>& vec, elem_type value) {
for ( int i = 0; i < vec.size(); ++i) {
if ( vec[i] == value ) {
return &vec[i];
}
}
return 0;
}
int main( int argc, char **argv) {
int arr[10] = {1,2,3,4,5,6,7,8,9,10};
std::vector<int> vec( arr, arr+10);
int value = 9;
int *ptr1 = find2(vec,value);
}
以下是编译错误
1> d:\personal\work\find\find\find.cpp(25) : see reference to function template instantiation 'elem_type *find2<int>(std::vector<_Ty> &,elem_type &)' being compiled
1> with
1> [
1> elem_type=int,
1> _Ty=int
1> ]
编译器是Visual Studio 11
最好使用与容器中使用的索引相同类型的变量。 在这种情况下,您需要一个size_t
或一个size_type
。 它们与向量的size和operator []函数中使用的类型相对应。
for (size_t i = 0; i < myVector.size(); ++i)
{
myVector[i]++;
}
如果您需要反向迭代,只需维护一个内部索引。
for (size_t i = 0; i < myVector.size(); ++i)
{
size_t j = myVector.size() - i - 1;
myVector[j]++;
}
如果您需要执行带符号的数学运算,请再次维护内部转换。
for (size_t i = 0; i < myVector.size(); ++i)
{
int j = (int)i;
myVector[i] += j;
}
您的基本问题是要混合有符号和无符号整数。 您的索引变量是有符号类型,但是向量的size()成员函数返回无符号类型。 这样的混合类型可能会导致错误。 如果将诸如-1之类的有符号值分配给无符号变量,则通常会得到非常大的值。
遍历标准库容器的惯用方式是使用标准库迭代器。
for (std::vector<elem_type>::iterator it=vec.begin(); it<vec.end(); ++it)
{
if ( *it == value ) {
return &(*it);
}
}
在这一行,
for ( int i = 0; i < vec.size(); ++i ) {
您正在将带符号的int
变量i
与vec.size()
的无符号的size_t
结果进行vec.size()
。
编译器发出警告,因为面对C ++中的隐式提升 ,这种比较是不安全的。 i
被提升为size_t
。 如果i
(假设)为负,那将产生非常大的价值,并因此产生意想不到的比较结果。
一个简单的方法是
#include <stddef.h>
typedef ptrdiff_t Size;
typedef Size Index;
然后做例如
for ( int i = 0; i < Size( vec.size() ); ++i ) {
您可能会得到至少一个答案,建议您看似简单一些
for ( size_t i = 0; i < vec.size(); ++i ) {
但这是有问题的,原因是编译器警告过同样的原因:使用无符号整数作为数字可能会导致非常奇怪和意外的结果,错误的结果,这是由于隐式提升以及通常从负数到无符号的转换,反之亦然。
比上面的转换更好,定义一个countOf
函数,例如
template< class Container >
Size countOf( Container const& c ) { return v.size(); }
template< class Elem, Size n >
Size countOf( Elem (&)[n] ) { return n; }
然后只写
for ( int i = 0; i < countOf( vec ); ++i ) {
最好不要忘记建立索引并使用迭代器:
for ( auto it = vec.begin(); it != vec.end(); ++it ) {
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.