2

I have a function which has exactly the same code for many basic types. To save code lines, I want to declare it as template and instantiate it explicitly for all later used types once: declaration in header file and implementation + explicit instantiation in cpp file (same design as writing normal function bibs).

My approach was:

// header.h
template <class T> T func (T arg);


// header.cpp
#include "header.h"

template <class T> T func (T arg)
{
    // implementation...
}
template int func<int> (int arg);
template double func<double> (double arg);

However, on parashift, I found this form of declaration:

// header.h
template <typename T> extern void foo();

What is the sense of extern here? How differs it from my approach? What is correct?

Also normal functions never have to be declared extern. It would be different if it was extern template void foo<int>(); (see accepted answer here), what would prohibit the compiler to instatiate a template that is already implemented in the header file.

Edit:

Is

// header.h
int func (int arg);
double func (double arg);

// header.cpp
#include "header.h"

int func (int arg)
{ ... }
double func (double arg)
{ ... }

not completely analogous/equivalent to

// header.h
template <class T> T func (T arg);
// here is the question: like above or template <class T> extern T func (T arg); ???

// header.cpp
#include "header.h"

template <class T> T func (T arg)
{ ... }
template int func<int> (int arg);
template double func<double> (double arg);

concerning later usage

// main.cpp
#include "header.h"

int main ()
{
    // for overloading
    func(20);
    func(20.0);
    func((int)20.0);

    // for template
    func(20); // == func<int>(20)
    func(20.0); // == func<double>(20.0)
    func((int)20.0); // == func<int>((int)20.0)
    func<int>(20.0); // == func<int>((int)20.0)

    return 0;
}
Community
  • 1
  • 1
mb84
  • 683
  • 1
  • 4
  • 13

1 Answers1

0

Your syntax is declaring in the header file that there exists somewhere a template <class T> T func (T arg); which would still not let user have the code using that template function, but would let having template code doing that (which compiler won't be able to instantiate without having seen the template function definition).

The FAQ section you refer to is featuring the syntax declaring that there exists an instantiation of template for certain class X somewhere and the compiler, when seeing X x = func(X()); should not be instantiating a template but rather leave the symbol unresolved and let linker deal with it.

bobah
  • 18,364
  • 2
  • 37
  • 70
  • I want to let the compiler know that there is a collection of functions `template T func (T arg);` available and the linker be able to find *one and only* instatiation of them in the cpp file. Like if I had written a normal overloaded function bib in the usual header/cpp design (see my edit). – mb84 Feb 03 '14 at 12:10