将向量传递给模板函数
Posted
技术标签:
【中文标题】将向量传递给模板函数【英文标题】:Passing a vector to a template function 【发布时间】:2011-07-29 14:37:20 【问题描述】:这是我正在尝试编写的一个小函数,用于跟踪我在函数中使用的动态分配(厌倦了一直写 delete [])。
template <class T>
T* snew(int size, vector<T*> list)
T* pointer = new T[size];
list.push_back(pointer);
return pointer;
vector<float*> list;
float* myfloat1 = snew<float*>(HEIGHT*WIDTH,list);
float* myfloat2 = snew<float*>(HEIGHT*WIDTH,list);
float* myfloat3 = snew<float*>(HEIGHT*WIDTH,list);
那么当我需要清除我可以使用的内存时:
template <class T>
void sdelete(vector<T*> list)
vector<T*>::iterator it;
for (it = list.begin(); it != list.end(); ++it)
delete [] *it
*it = NULL
像这样:
sdelete<float*>(list);
当我尝试编译时,我得到:
cannot convert parameter 2 from 'std::vector<_Ty>' to 'std::vector<_Ty,_Ax>'
不知道是什么意思。感谢您的洞察力:)
【问题讨论】:
如果你想要一个多维数组,请使用向量的向量或 Boost.MultiArray。 您是否考虑过为此使用智能指针或仅使用标准库容器之一?您不需要在应用程序代码中到处写delete
;如果您这样做,则很可能您的代码不正确并且不是异常安全的。
正如@James 提到的,智能指针可能是您所需要的。 boost::shared_array
是一个不错的例子。
@Sander,为什么vector<float>(WIDTH*HEIGHT)
不是一个好的容器?
为什么不用向量来存储数据?而不是一个向量来跟踪数据?奇数。
【参考方案1】:
首先,您通过值传递vector<T*> list
,这意味着它被复制并且您的全局list
保持不变。
这样做:
template <class T>
T* snew(int size, vector<T*>& list)
关于编译问题,有错别字,*
一次申请太多了,把用法改成
float* myfloat1 = snew<float>(HEIGHT*WIDTH,list);
sdelete<float>(list);
或者你甚至可以依赖编译器的类型推断并直接编写
float* myfloat1 = snew(HEIGHT*WIDTH,list);
sdelete(list);
但是这个想法作为一个整体是非常糟糕的,因为如果你已经有一个vector
,你不想手动做new/delete
。只需创建一个 vector<float> x(HEIGHT*WIDTH);
并使用它,它就会自动删除。
【讨论】:
好的,所以向量是与任何其他类型一样的类型,而不是指针,所以如果我想通过引用传递它,我需要做 &, ;) 请注意,当您阅读并粘贴编译错误cannot convert parameter 2 from 'std::vector<_Ty>' to 'std::vector<_Ty,_Ax>'
时,您忘记在其中包含模板参数(稍后或在下一行指定)。他们会立即向您透露这个问题!【参考方案2】:
使用
snew<float>(HEIGHT*WIDTH,list);
或者更好,简单
snew(HEIGHT*WIDTH,list);
确实,模板参数snew
是T
,而你传递了vector<T*>
。要匹配vector<float*>
,您必须通过float
。
然而,当调用函数模板时,参数可以被推导出来,所以你根本不需要把<float>
这个东西。
但是,我能给你的最好建议是忘记这一切,使用vector<vector<float>>
。
【讨论】:
我明白你的意思是因为我在函数定义中指定了 T*,所以我不需要说 T*,而在调用中只说 T以上是关于将向量传递给模板函数的主要内容,如果未能解决你的问题,请参考以下文章