473,597 Members | 2,157 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

defaults for template'd functions

Hey all,

I've been running into a problem with default values to template'd
functions. I've boiled down my problem to this simple example code:

#include<iostre am>

using namespace std;

// function object
template<typena me Valuestruct function {
void operator()(Valu e v) {
cout << '*' << v << '*' << endl;
}
};

template<typena me Value, typename Function>
void do_it(Value v, Function f = function<Value> ()) {
cout << v << '\t';
f(v);
}

int main(int argc, char* argv[]) {
do_it(3);
return 0;
}

Basically, I want the second parameter of do_it to be anything that can
be called like a function with a single argument of type Value but I
want the default to be the default constructed object of type
function<Value> (). That's what I want, but what I get is this error:

test.cpp:19: error: no matching function for call to 'do_it(int)'

It doesn't seem to be recognizing my default. If I change the call to
do_it to:

do_it<int, function<int(3) ;

i.e explicitly give the type of the default in int case, it works fine.
But I don't want to have to give it the default type every time I call
it, then I wouldn't even bother with making it a default.

So, I figured if I give a default for the typename and well as the
value it might work:

template<typena me Value, typename Function = function<Value
void do_it(Value v, Function f = function<Value> ()) {
cout << v << '\t';
f(v);
}

but then I get this error:

test.cpp:13: error: default template arguments may not be used in
function templates

Any idea why none of this isn't working? Am I asking C++ to do to much
type inference? I also don't understand why I'm getting the error at
the function call and not the function declaration.

P.S. I'm compiling this with gcc version 4.0.1 (Apple Computer, Inc.
build 5250). Here's the full g++ -v:

Using built-in specs.
Target: i686-apple-darwin8
Configured with: /private/var/tmp/gcc/gcc-5250.obj~12/src/configure
--disable-checking -enable-werror --prefix=/usr --mandir=/share/man
--enable-languages=c,obj c,c++,obj-c++
--program-transform-name=/^[cg][^.-]*$/s/$/-4.0/
--with-gxx-include-dir=/include/c++/4.0.0 --build=powerpc-apple-darwin8
--with-arch=pentium-m --with-tune=prescott --program-prefix=
--host=i686-apple-darwin8 --target=i686-apple-darwin8
Thread model: posix
gcc version 4.0.1 (Apple Computer, Inc. build 5250)

-krish

Jan 13 '07 #1
5 1735
kr***********@g mail.com wrote:
Hey all,

I've been running into a problem with default values to template'd
functions. I've boiled down my problem to this simple example code:

#include<iostre am>

using namespace std;

// function object
template<typena me Valuestruct function {
void operator()(Valu e v) {
cout << '*' << v << '*' << endl;
}
};

template<typena me Value, typename Function>
void do_it(Value v, Function f = function<Value> ()) {
cout << v << '\t';
f(v);
}

int main(int argc, char* argv[]) {
do_it(3);
return 0;
}

Basically, I want the second parameter of do_it to be anything that can
be called like a function with a single argument of type Value but I
want the default to be the default constructed object of type
function<Value> (). That's what I want, but what I get is this error:

test.cpp:19: error: no matching function for call to 'do_it(int)'
The problem is that there is now way to figure out the type of the
second type parameter in the "do_it(3)" function call. After all,
main() calls do_it() with only one argument, 3. So the compiler has to
figure out what type a second argument would have been - if main() had
called do_it() with two arguments (instead the one argument) that
main() passed in the actual call.

Of course, there is no way to ascertain the type of an absent argument
- nor can the program ever be able to answer that question. So another
approach is needed to solve this problem. And that solution would be to
have the program provide a second parameter whenever one is not present
in the call to do_it(). In this way the program can pick whatever type
it likes that argument to be (in the case, the choice will be
function<Value> ):

#include <iostream>

using std::cout;
using std::endl;

template< class Value>
struct function
{
void operator()(Valu e v)
{
cout << '*' << v << '*' << endl;
}
};

template< class Value, class Function>
void do_it( Value v, Function f )
{
cout << v << '\t';
f(v);
}

template< class Value>
void do_it( Value v)
{
do_it( v, function<Value> ());
}

int main()
{
do_it(3);
}

With two do_it() overloads, calling do_it() with one argument forwards
the call to the other do_it(), providing its own the Function<Value>
object as the "missing", second parameter. Essentially, the program has
implemented C++'s default argument behavior for the do_it() function
all on its own.

Greg

Jan 13 '07 #2
kr***********@g mail.com wrote:
Hey all,

I've been running into a problem with default values to template'd
functions. I've boiled down my problem to this simple example code:

#include<iostre am>

using namespace std;

// function object
template<typena me Valuestruct function {
void operator()(Valu e v) {
cout << '*' << v << '*' << endl;
}
};

template<typena me Value, typename Function>
void do_it(Value v, Function f = function<Value> ()) {
cout << v << '\t';
f(v);
}

int main(int argc, char* argv[]) {
do_it(3);
return 0;
}

Basically, I want the second parameter of do_it to be anything that can
be called like a function with a single argument of type Value but I
want the default to be the default constructed object of type
function<Value> (). That's what I want, but what I get is this error:

test.cpp:19: error: no matching function for call to 'do_it(int)'
The problem is that there is no way to figure out the type of the
second type parameter in the "do_it(3)" function call. After all,
main() calls do_it() with only one argument, 3. So the compiler has to
figure out what type a second argument would have been - if main() had
called do_it() with two arguments (instead the one argument) that
main() passed in the actual call.

Of course, there is no way to ascertain the type of an absent argument
- nor can the program ever be able to answer that question. So another
approach is needed to solve this problem. And that solution would be to
have the program provide a second parameter whenever one is not present
in the call to do_it(). In this way the program can pick whatever type
it likes that argument to be (in the case, the choice will be
function<Value> ):

#include <iostream>

using std::cout;
using std::endl;

template< class Value>
struct function
{
void operator()(Valu e v)
{
cout << '*' << v << '*' << endl;
}
};

template< class Value, class Function>
void do_it( Value v, Function f )
{
cout << v << '\t';
f(v);
}

template< class Value>
void do_it( Value v)
{
do_it( v, function<Value> ());
}

int main()
{
do_it(3);
}

With two do_it() overloads, calling do_it() with one argument forwards
the call to the other do_it(), providing its own the Function<Value>
object as the "missing", second parameter. Essentially, the program has
implemented C++'s default argument behavior for the do_it() function
all on its own.

Greg

Jan 13 '07 #3
On Jan 12, 10:01 pm, "Greg" <gre...@pacbell .netwrote:
krishnaros...@g mail.com wrote:
Hey all,
I've been running into a problem with default values to template'd
functions. I've boiled down my problem to this simple example code:
#include<iostre am>
using namespace std;
// function object
template<typena me Valuestruct function {
void operator()(Valu e v) {
cout << '*' << v << '*' << endl;
}
};
template<typena me Value, typename Function>
void do_it(Value v, Function f = function<Value> ()) {
cout << v << '\t';
f(v);
}
int main(int argc, char* argv[]) {
do_it(3);
return 0;
}
Basically, I want the second parameter of do_it to be anything that can
be called like a function with a single argument of type Value but I
want the default to be the default constructed object of type
function<Value> (). That's what I want, but what I get is this error:
test.cpp:19: error: no matching function for call to 'do_it(int)'

The problem is that there is no way to figure out the type of the
second type parameter in the "do_it(3)" function call. After all,
main() calls do_it() with only one argument, 3. So the compiler has to
figure out what type a second argument would have been - if main() had
called do_it() with two arguments (instead the one argument) that
main() passed in the actual call.

Of course, there is no way to ascertain the type of an absent argument
- nor can the program ever be able to answer that question.
That makes sense. And the compiler doesn't want to infer the 'default'
type from the default value of the second parameter?

Then in theory, I should be able to give a default type for the
Function template parameter and it should work? Or is there some reason
that wouldn't work as well? And why won't gcc let you give defaults to
template parameters for functions? Is there a fundamental reason it
doesn't allow this?
So another approach is needed to solve this problem. And that solution
would be to have the program provide a second parameter whenever one
is not present in the call to do_it(). In this way the program can pick whatever
type it likes that argument to be (in the case, the choice will be
function<Value> ):

#include <iostream>

using std::cout;
using std::endl;

template< class Value>
struct function
{
void operator()(Valu e v)
{
cout << '*' << v << '*' << endl;
}
};

template< class Value, class Function>
void do_it( Value v, Function f )
{
cout << v << '\t';
f(v);
}

template< class Value>
void do_it( Value v)
{
do_it( v, function<Value> ());
}

int main()
{
do_it(3);
}

With two do_it() overloads, calling do_it() with one argument forwards
the call to the other do_it(), providing its own the Function<Value>
object as the "missing", second parameter. Essentially, the program has
implemented C++'s default argument behavior for the do_it() function
all on its own.
Thanks a lot for your help and solution!

-krish

Jan 13 '07 #4
kr***********@g mail.com wrote:
That makes sense. And the compiler doesn't want to infer the 'default'
type from the default value of the second parameter?

Then in theory, I should be able to give a default type for the
Function template parameter and it should work? Or is there some reason
that wouldn't work as well? And why won't gcc let you give defaults to
template parameters for functions? Is there a fundamental reason it
doesn't allow this?
Default type parameters for function templates have been added to the
C++ working draft. So I would expect them to be part of the next C++
language Standard. So your solution should work in the future - just
probably not today - with your current C++ compiler.

Greg

Jan 13 '07 #5
kr***********@g mail.com wrote:
That makes sense. And the compiler doesn't want to infer the 'default'
type from the default value of the second parameter?

Then in theory, I should be able to give a default type for the
Function template parameter and it should work? Or is there some reason
that wouldn't work as well? And why won't gcc let you give defaults to
template parameters for functions? Is there a fundamental reason it
doesn't allow this?
Default type parameters for function templates have been added to the
C++ working draft. So I would expect them to be part of the next C++
language Standard. So your suggested solution (not the original
program) should be possible in the future - just probably not today -
with your current C++ compiler.

Greg

Jan 13 '07 #6

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

4
1493
by: velthuijsen | last post by:
I've been reading (and using the examples in) Thinking in C++ (vol 2). One of the things that the author shows you can do with templates is the following: #include <iostream> using namespace std; template<class T> class Counted
0
1629
by: Chris F Clark | last post by:
In our C++ project we have some internal bug reporting macros that we use to get useful information when the program does something unexpected. Essentially at the point of the error, we invoke an internal interactive debugger that knows the classes within our system and allow us to walk around the objects that exist at the time of the fault. It mostly works fairly well. That catch being that we have to hand implement some of the code...
8
11355
by: vpadial | last post by:
Hello, I want to build a library to help exporting c++ functions to a scripting languagge. The scripting language provides a function to register functions like: ANY f0() ANY f1(ANY) ANY f2(ANY, ANY) ANY f3(ANY, ANY, ANY)
9
2725
by: Ann Huxtable | last post by:
I have the following code segment - which compiles fine. I'm just worried I may get run time probs - because it looks like the functions are being overloaded by the return types?. Is this Ok: ? template <class T1, class T2> int getValue( T1 col, T2 row ) ; template <class T1, class T2> double getValue( T1 col, T2 row ) ;
2
1764
by: Drew McCormack | last post by:
I have a self written Tensor class which I need to write a number of elementwise operations for (eg sin, cos, abs, conj). I am trying to implement most of these in terms of standard library functions. Unfortunately, not all functions in the standard library are constructed the same (eg some are template functions, some use pass-by-value where others use pass by reference). To get around this, I have tried to come up with an adaptor...
5
1605
by: Mark Fox | last post by:
Hello, When you add a new web form in VS.NET it automatically adds the following namespaces at the top: using System; using System.Collections; using System.ComponentModel; using System.Data; using System.Drawing;
3
3746
by: Hamilton Woods | last post by:
Diehards, I developed a template matrix class back around 1992 using Borland C++ 4.5 (ancestor of C++ Builder) and haven't touched it until a few days ago. I pulled it from the freezer and thawed it out. I built a console app using Microsoft Visual C++ 6 (VC++) and it worked great. Only one line in the header file had to be commented out. I built a console app using Borland C++ Builder 5. The linker complained of references to...
5
2260
by: StephQ | last post by:
This is from a thread that I posted on another forum some days ago. I didn't get any response, so I'm proposing it in this ng in hope of better luck :) The standard explanation is that pointer to functions are hard to inline for the compiler, and so you won't be able to avoid function call overhead. This is an important aspect when you are calling a function very frequently for evaluation reason: think of the problem of performing...
2
1759
by: vectorizor | last post by:
Hello all, I am attempting to vectorize few template functions with the Intel compiler, but without much success so far. Ok granted, this question is not 100% c++, but it is related enough that I felt I could post it here. Also, I did ask in the Intel forums, without much success. And maybe there are some c++ coders in here that are familiar with the Intel compiler. The code below highlights the problem I have. Essentially, I have a
0
7885
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
8271
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
1
8031
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
6686
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
1
5847
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
5426
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
1
2399
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
1
1493
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.
0
1231
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.