在 C++ 中,如何编写函数以便它可以处理任何数据类型?
In C++, how to write a function so that it can work on any data type?
我正在使用此资源学习 C++ STL:http://community.topcoder.com/tc?module=Static&d1=tutorials&d2=standardTemplateLibrary
下面给出了反转数组元素的函数:
template<typename T> void reversearr(T *begin, T *end) {
// We should at first decrement 'end'
// But only for non-empty range
if(begin != end)
{
end--;
if(begin != end) {
while(true) {
swap(*begin, *end);
begin++;
if(begin == end) {
break;
}
end--;
if(begin == end) {
break;
}
}
}
}
}
它适用于系统定义的类型数组,例如:
int arr[]={1,2,3,4,5}
reversearr(arr,arr+5);
但它给出了以下编译器错误:
"Iterator02_ReverseIterators.cpp:39:32: error: no matching function for call to 'reversearr(std::vector::iterator, std::vector::iterator)'"
如果我使用此代码:
vector<int> v;
//Code to insert data in vector
reversearr(v.begin(),v.end());
如何编写类似的函数以便它们也可以在迭代器上工作?
好吧,cppreference.com 再次为我们提供了完整的答案,也称为 std::reverse
:
可能的实现:
template<class BidirIt>
void reverse(BidirIt first, BidirIt last)
{
while ((first != last) && (first != --last)) {
std::iter_swap(first++, last);
}
}
其中 BidirIt
是 bidirectional iterator 类型的 概念 。标准库容器的迭代器和原始指针都满足它,这就是它起作用的原因。
在你的代码中,参数是T
的指针。当你使用迭代器时,参数是指向迭代器的指针,所以它不起作用。
如果你想让它和迭代器一起工作,我想你应该这样写:
template<typename T>
void reversearr(T begin, T end)
{
...
}
这是一个有趣的事实:
即使您从参数中删除 *
,您的代码也适用于数组。
template<typename T> void reversearr(T begin, T end) {
为什么?
因为在你原来的代码中,T
是int
,而函数参数的T*
是int*
。
在我修改后的代码中,T
为int*
,函数参数为stillint*
.
并且这个 "version" 与迭代器一起工作 - 选择迭代器的语法和语义,以便您可以编写与指针或迭代器同样有效的通用函数。
我正在使用此资源学习 C++ STL:http://community.topcoder.com/tc?module=Static&d1=tutorials&d2=standardTemplateLibrary
下面给出了反转数组元素的函数:
template<typename T> void reversearr(T *begin, T *end) {
// We should at first decrement 'end'
// But only for non-empty range
if(begin != end)
{
end--;
if(begin != end) {
while(true) {
swap(*begin, *end);
begin++;
if(begin == end) {
break;
}
end--;
if(begin == end) {
break;
}
}
}
}
}
它适用于系统定义的类型数组,例如:
int arr[]={1,2,3,4,5}
reversearr(arr,arr+5);
但它给出了以下编译器错误:
"Iterator02_ReverseIterators.cpp:39:32: error: no matching function for call to 'reversearr(std::vector::iterator, std::vector::iterator)'"
如果我使用此代码:
vector<int> v;
//Code to insert data in vector
reversearr(v.begin(),v.end());
如何编写类似的函数以便它们也可以在迭代器上工作?
好吧,cppreference.com 再次为我们提供了完整的答案,也称为 std::reverse
:
可能的实现:
template<class BidirIt>
void reverse(BidirIt first, BidirIt last)
{
while ((first != last) && (first != --last)) {
std::iter_swap(first++, last);
}
}
其中 BidirIt
是 bidirectional iterator 类型的 概念 。标准库容器的迭代器和原始指针都满足它,这就是它起作用的原因。
在你的代码中,参数是T
的指针。当你使用迭代器时,参数是指向迭代器的指针,所以它不起作用。
如果你想让它和迭代器一起工作,我想你应该这样写:
template<typename T>
void reversearr(T begin, T end)
{
...
}
这是一个有趣的事实:
即使您从参数中删除 *
,您的代码也适用于数组。
template<typename T> void reversearr(T begin, T end) {
为什么?
因为在你原来的代码中,T
是int
,而函数参数的T*
是int*
。
在我修改后的代码中,T
为int*
,函数参数为stillint*
.
并且这个 "version" 与迭代器一起工作 - 选择迭代器的语法和语义,以便您可以编写与指针或迭代器同样有效的通用函数。