A function template defines one function pattern that the compiler can use for different element types. It avoids unsafe polymorphic array handling while preserving each array's actual type. section 8.10
For arrays of base and derived objects, templated printing and deletion functions provide readable duplication without passing derived arrays through base-class interfaces. This preserves correct destruction and avoids allocation or deallocation mismatches. section 8.10
Listing 8.20 Functions without polymorphic array passing
const int SIZE = 4;
class B {
private:
int n;
public:
B(int n=0) : n(n) {}
~B() { std::cout << "destroying B\n"; }
int getN() const { return n; }
};
class D : public B {
int m;
public:
D() : B(1), m(2) {}
~D() { std::cout << "destroying D\n"; }
};
template <typename T> #1
void printArray(T a[]) {
for (int i = 0; i < SIZE; ++i)
std::cout << a[i].getN() << '\n';
}
template <typename T> #2
void deleteArray(T a[]) {
delete [] a;
}
int main() {
B* bs = new B[SIZE];
printArray(bs); #3
deleteArray(bs);
D* ds = new D[SIZE];
printArray(ds); #4
deleteArray(ds);
return 0;
}
A complete example declares printArray and deleteArray as templates, then instantiates them separately for B* and D* arrays. section 8.10
Correct destruction for derived arrays
Calling the templated functions with D* prints derived values and destroys each D followed by its B subobject, unlike the unsafe base-array approach. section 8.10
Function templates also support focused reuse: a filtering function can accept a comparison parameter, with std::greater<double> or std::less<double> supplying the comparison behavior. section 11.10

