Difference between using function overloading and function templates

V

Victor Bazarov

WittyGuy said:
What is the major difference between function overloading and
function templates?

Overloaded function set is predefined and limited (bounded). The set
of functions generated from a template can (and usually is) unbounded.

The rules for overload resolution are slightly different. For example,
to determine if a template can represent a viable function that should
participate in the name resolution, the template arguments need to be
deduced. If they cannot be deduced, the template cannot be instantiated
and is not a viable function.

I am certain there are more, but I just can't think of any at the moment.

Have you tried any books? Like "C++ Templates" by D. Vandevoorde and
N. Josuttis... It's very good.

V
 
W

WittyGuy

So, is function template is much better than function overloading? (in
performance?)

Wg
 
F

Ferdi Smit

WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?

They match differently. And function templates take arbitrary types.
Consider this:

#include <iostream>
using namespace std; // small test program, it's ok

void f(double i) {cout << "f(double)" << endl;}
//void f(float i) {cout << "f(float)" << endl;}

template <typename T>
void f(T i) {cout << "template" << endl;}


int main() {
f(1);
f(1.0f);

return 0;
}

What will this output? Well, the first call will go to the template function
f<int>, because that's the best match. The second will also go to the
template function f<float> because that too is the best match. Notice how it
doesn't perform a conversion from float to double, to call f(double). Would
we add the f(float) function, that one would get called. Also, if we remove
the function template, then a conversion from float to double is made, and
f(double) is called. Finally, we can call the function template with any
type; even for example with an std::list. I'm not sure if this answers your
question, since it was so general...nonetheless I think this ought to
clarify some differences.



[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
C

Carlos Moreno

WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?

Homework alarm triggered !!

Hints:

Do you understand the concept of function overloading?

Function templates?

What do you feel is the difference between these two:

// option 1 ---------------------------
void swap (int & a, int & b)
{
int tmp = a; a = b; b = tmp;
}

void swap (double & a, double & b)
{
double tmp = a; a = b; b = tmp;
}

// ------------------------------------

// option 2 ---------------------------

template <typename T>
void swap (T & a, T & b)
{
T tmp = a; a = b; b = tmp;
}


This example should answer the question, if you understand the
basic concepts.

HTH,

Carlos
 
C

Carl Barron

WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?

Thanks!
Templates [functions and classes] describe to the compiler a family of
items [functions or classes] in terms of parameters. That
understatement leads to a solution of a problem write a function that
returns a object 'twice as big' as its argument.

template <class T>
T twice (const T &x)
{
T t(x);
return t+=x;
}

will generate a function requiring T::eek:perator +=() to exist for any
type T used in a function call.

overloading is a specific set of functions with the same name and
arguments. Only the explicitly created functions exist and most likely
each overload needs its own code.

Also non-template overloads use the one implicit conversion process and
templates do not us any implict conversion process.

int twice_1(int x) {return x+x;}
std:string twice(std::string const &x) { std::string t(x);return t+=x;}

int main()
{
double c = 3.5;
c = twice(c); // compiles;
c = twice_1(c): // error twice_1(double) does not match
twice(int),twice(std::string);

}

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
G

Greg

WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?

Thanks!

I would say the "major" difference between a function template and an
overloaded function is that the compiler discriminates against a
function template whenever it seeks a match for a function call in the
source code. When it can, the compiler will prefer to call an
overloaded function instead of having to instantiate a function
template for any function call appearing in source code.

The consequences of this bias are interesting. Especially surprising to
many is that a specialized function template is not considered for a
match, unless the function template it specializes is first determined
to be the best match of all available candidate functions. The
implication of this policy is that the C++ compiler will not call a
specialized template function - even if its declaration is an exact
match for the function call in the source code - if there is even one
function overload that the compiler deems a better match than the
function template with the specialization that matches exactly. Well,
that was a mouthful!

Of course, one might expect that the reason for specializing the
function template would be to ensure that it gets called whenever a
function call in the source code uses parameters that match its
specialized types exactly. And in fact, that is how it works - for
overloaded functions (and usually an overloaded function is what the
developer really wanted to write here.)

A specialized function template is not to ensure a match for a function
call. Rather the specialized version merely tells the compiler how to
instantiate the function template for its particular parameter types,
should the function template it specializes ever be the best match for
a function call in the source code.

Greg


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
K

kwikius

Carlos said:
WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?
[snip]

// ------------------------------------

// option 2 ---------------------------

template <typename T>
void swap (T & a, T & b)
{
T tmp = a; a = b; b = tmp;
}

And of course dont forget overloaded function templates:

template <typename TL, typename TR>
void swap(TL & l, TR & r)
{
TL tmp = l; l=r ; r = tmp;
}

Andy Little


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
K

kanze

WittyGuy said:
What is the major difference between function overloading
and function templates?

As Carlos said, this stinks of homework. But it's a pretty bad
question, if it is -- far to general for an intelligent student
to know what is really being asked.

I would start by saying that the two aren't really related; they
work on completely different levels. Basically, function
overloading allows the definition of more than one function with
the same name, and provides a means of choosing between the
functions based on parameter matching. Template functions are a
means of specifying to the compiler how to create new functions,
based on the instantiation type. A template function itself
isn't a function, and doesn't intervene in function overloading.
Functions generated from the template (instantiations) however,
behave like normal functions, and do participate in overload
resolution.

Basically, when the compiler encounters a function call, it will
first look up the name, according to the scope of the call. All
functions with the name, in the same scope, will be taken as the
overload set. If the name corresponds to a template function,
the compiler will, if possible, instantiate that function, and
add the generated function to the overload set. (And of course,
this is done for all applicable template functions.) It then
applies the rules of overload generation to the set, to choose
which function it calls.

IMHO, the keys to understanding this are 1) a function template
is not a function, it is only a recepe for the compiler to
produce a function, 2) the rules for deciding whether to produce
a function from a function template, and which function to
produce, are independant of the rules for overload resolution,
and 3) the decisions concerning the template function are taken
before starting overload resolution.

Finally, once the overload set has been constructed, the fact
that a function is the instantiation of a template does play a
role in overload resolution. Basically, if two functions are
equally good matches, and one is the instantiation of a
template, and the other isn't, the one that isn't wins, and if
two functions are equally good matches, and both are
instantiations of a template function, then the one whose
template is the most specialized wins. But such subtilities are
part of what I would consider advanced C++.

--
James Kanze GABI Software
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
K

kanze

Greg said:
WittyGuy wrote:
I would say the "major" difference between a function template
and an overloaded function is that the compiler discriminates
against a function template whenever it seeks a match for a
function call in the source code. When it can, the compiler
will prefer to call an overloaded function instead of having
to instantiate a function template for any function call
appearing in source code.

The way I understand it, that's not quite what happens (although
I think it was with several pre-standard compilers). The
decision to try to instantiate the template function takes place
independantly of overloading. If the compiler can instantiate
the *declaration* without an error, the resulting function is
added to the overload set.

If two functions are otherwise equally good matches, and one is
the result of instantiating a template function, and the other
not, overload resolution will choose the one that isn't. Note,
however, that the results of instantiating a template function
will often be an exact match; if the non template function
requires some non-trivial conversions, the template
instantiation will be preferred. (This is, I think, a
significant difference between the standard and most
pre-standard compilers. Difference largely attenuated by the
fact that most pre-standard compilers had so many problems with
templates that you only did the simplest things with them, so
the problem cases don't occur.)

As I understand it (and I'm not 100% certain here), until
overload resolution is finished, only the function declaration
is instantiated, and an error in the instantiation isn't a
program error, but only means that the instance will not be
considered in overload resolution. Once overload resolution has
finished, if the chosen function is an instance of a template,
the compiler will instantiate the definition. Any errors at
this time *are* compiler error -- the compiler will not go back
and try overload resolution without considering the function.

--
James Kanze GABI Software
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
C

Carlos Moreno

kwikius said:
And of course dont forget overloaded function templates:

template <typename TL, typename TR>
void swap(TL & l, TR & r)
{
TL tmp = l; l=r ; r = tmp;
}

Hmmm, now that I think about it... Shouldn't *this* be the way to
define a swap template?? I mean, why would you need the other version,
once you have this one? If you call swap with the parameters of the
exact same type, this one will match and will do the right thing (it
will do *exactly* the same as the other one).

Still, what you're saying applies to things like:

template <typename T>
void swap (vector<T> & a, vector<T> & b)
{
a.swap (b);
}

(this is probably already done in most standard library implementations,
I guess -- for STL containers, std::strings, etc.)

Carlos
 
T

Tokyo Tomy

WittyGuy said:
Hi,
What is the major difference between function overloading and function
templates?

All posters write the differences mainly from the viewpoint of
matching order so far. I would like to write one of the differences
from the viewpoint of call convention.

If you use template function instead of overloaded function, you can
call the template function in the form of f<int>( ), but you cannot
use this form for the overloaded function.

Overload on return is inhibited in the Standard.

int f( ) { };
double f( ) { }; // error

This is because the compiler cannot differentiate the two functions
with the call convention f( ).

However, the call convention f<int>( ) and f<double>( ) of function
template can tell the compiler which function should be selected.

I show example codes, although I don't say that the usage of this call
convention for this purpose is a good one. Somebody may know more
appropriate examples..

#include <iostream>
using namespace std;

template<typename ReturnType>
ReturnType f() { };

template<>
int f<int>() {
cout << "int f()" << endl;
return 3;
}

template<>
double f<double>() {
cout << "long f()" << endl;
return 3.14;
}

int main()
{
cout << f<int>() << endl;
cout << f<double>() << endl;
return 0;
}

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
V

Victor Bazarov

Tokyo said:
WittyGuy said:
Hi,
What is the major difference between function overloading and
function templates?

All posters write the differences mainly from the viewpoint of
matching order so far. I would like to write one of the differences
from the viewpoint of call convention.

If you use template function instead of overloaded function, you can
call the template function in the form of f<int>( ), but you cannot
use this form for the overloaded function.

Overload on return is inhibited in the Standard.

int f( ) { };
double f( ) { }; // error

This is because the compiler cannot differentiate the two functions
with the call convention f( ).
[..]

No, but you can do

int (*pf)() = f; // will pick up the 'int f()'
pf(); // will call it

V
 
S

sreenu

the main difference between function overloading and function
template(gerneric function) is :
function overloading should be exact match of its prototype.where as
there is no such rule for generic function.


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
F

Francis Glassborow

sreenu said:
the main difference between function overloading and function
template(gerneric function) is :
function overloading should be exact match of its prototype.where as
there is no such rule for generic function.


I have read this several times but it still seems to have it exactly
backwards. Overload resolution is by best match not exact match.

--
Francis Glassborow ACCU
Author of 'You Can Do It!' see http://www.spellen.org/youcandoit
For project ideas and contributions: http://www.spellen.org/
youcandoit/projects


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 
P

PJJ

The practical differences I think are (somewhat of a newbie so forgive any
inaccuracies)

On one hand function templates:
Are more flexible in that they work for types that don't yet exist!
e.g. A friendly programmer thinking of his collegues in the future, can
provide a function template for 'swap' which in most/many cases it will work
on new types. The current programmer can provide an algorithm that will be
useful to future programmers with future types in future code (as long as
all the types follow the same rules as the orignial type the template was
made for). E.g. 'swap' will for most standard objects. With a template, a
'swap' DOESN'T have to be written for each new type. The overloaded
functions only works for the types that exist. A new overloaded function has
to be created for each new type.
P.S. Even those types, that make sense to use the template function, but
don't quite fit the current template code, can be 'specialized'. Similar to
an overloaded function, in that they work with certain types only, a
particular version of the template must be written to match certain types
that don't generally conform. But there may be cases where no new code is
needed and the original authors function will work on many new types without
alteration.

On the other hand overloaded functions:
Are more flexible in the combinations of parmaters:
Currently I believe, with a function templates you can have a general case
that takes parameters of any type and a special case specialization for a
fixed set of know paramter types. What you can't do currently is partial
specialization where you specify a set of code for when you know the type of
some of the parameters but not all.
e.g. a swap( Unknown a, Unknown b) ok swap( int a, int b) have a special
version ok
swap( int a, Unknown b) not ok can't specify only some of the paramater
types.
Overloaded functions of course allow as many combinations as you are willing
to explicitly specify.
P.S. template classes, contrasting with function templates, do allow
partial specialization.

On the other hand with templates the compiler/you can get at a lot of
information
With templates the compiler knows a lot more about the types it is dealing
with. For instance C++ additions such as Loki and Boost allow a large number
of tests on the template types.
e.g. With a template function that can happily take a single item or a list,
the compiler can deduce what is being passed at compile time and
optimize/change accordingly.
Adding such knowledge to overloaded functions at compile time is harder.

On the other hand overloaded functions are safer?
I know many would disagree but with with vast numbers of template you can
get surprising situations. Because templates can match any type, certain
templates can be picked by the compiler that the programmer wasn't
expecting. I believe a change to class templates was made in respect to
this. When a class inherits a template, and within a function call is made,
which matches a global definition and an inherited template definition,
unlike standard class inheritance, compiler nowadays picks the global
definition. (Unless of course the tighter scope is specified in the call.).

On the other hand templates more fun to use:
I believe templates are extending C++ greatly and so trying to understand
them is a plus. If you have the time try being creative with templates.



[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,743
Messages
2,569,478
Members
44,898
Latest member
BlairH7607

Latest Threads

Top