www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - a quirk in function overloading

reply Hasan Aljudy <hasan.aljudy gmail.com> writes:
I've recently ran across a not-so-convenient behavior of overloading of 
functions, or rather, of function templates.
Before I go into details, I'd like to say that I know this behavior 
complies to the specs .. so please don't reply by saying "this is the 
intended behaviour!!!", I already know that.

So, what am I talking about?

suppose you have a function

void func( int x ) { ... }

and, say you wanted to overload it with

void func( char[] x ) { ... }

So far so good.
but, if you try to overload it with a templated function:

void func(T)() { ... }

woops!! template "func" conflicts with "func"!!

Problem: If you want to overload a function to take a "Type" as a 
parameter, you can't, because func(T)() is not a function, but a 
template with a function inside it, and, the template symbol name 
conflicts with the other "func" functions.

Yes, this is compliant to the specs, I know that, but I see this as a 
problem, because:
The traditional definition of function overloading is tied very much to 
the C language, where there are no templates.

D has templates, and much more, it has function templates.
Shouldn't function overloading be *re-designed* to account for this fact?

While it's true that function templates are not really functions, but 
rather, templates with functions inside them; while that's true, isn't 
it also true that when one writes a function templates, he actually 
thinks about it as a function? Otherwise, why was the
func( T params )( params ){ .. }
syntax introduced?

Please consider this concern.

I myself don't have much of an idea of how this problem could be 
resolved, so I'm just asking for this concert to be considered.

-Hasan
Dec 17 2006
next sibling parent Bill Baxter <dnewsgroup billbaxter.com> writes:
Hasan Aljudy wrote:
 I've recently ran across a not-so-convenient behavior of overloading of 
 functions, or rather, of function templates.
 Before I go into details, I'd like to say that I know this behavior 
 complies to the specs .. so please don't reply by saying "this is the 
 intended behaviour!!!", I already know that.
 
 So, what am I talking about?
 
 suppose you have a function
 
 void func( int x ) { ... }
 
 and, say you wanted to overload it with
 
 void func( char[] x ) { ... }
 
 So far so good.
 but, if you try to overload it with a templated function:
 
 void func(T)() { ... }
 
 woops!! template "func" conflicts with "func"!!

I think you can work around this somewhat using the dummy arg trick. See http://d.puremagic.com/issues/show_bug.cgi?id=337 You still can't have a function and a template coexist, but you can make a template that only matches one particular type with the dummy trick. Although then you may run into the problem that templates aren't as forgiving about matches of their regular parameters as normal functions: See http://d.puremagic.com/issues/show_bug.cgi?id=617
 Problem: If you want to overload a function to take a "Type" as a 
 parameter, you can't, because func(T)() is not a function, but a 
 template with a function inside it, and, the template symbol name 
 conflicts with the other "func" functions.
 
 Yes, this is compliant to the specs, I know that, but I see this as a 
 problem, because:
 The traditional definition of function overloading is tied very much to 
 the C language, where there are no templates.

No, C doesn't have any function overloading. That was added by C++ too. It requires name mangling, which C doesn't do.
 D has templates, and much more, it has function templates.
 Shouldn't function overloading be *re-designed* to account for this fact?

I fully agree that template overloading in D is something that needs work. The dummy=void workaround for overloading templates with other templates is really ugly, and the inability for templates and functions with the same name to coexist is a major annoyance as well.
 While it's true that function templates are not really functions, but 
 rather, templates with functions inside them; while that's true, isn't 
 it also true that when one writes a function templates, he actually 
 thinks about it as a function? Otherwise, why was the
 func( T params )( params ){ .. }
 syntax introduced?
 
 Please consider this concern.

I'm pretty sure this isn't the first time this issue has been discussed, and that Walter is aware that the current situation is sub-optimal. --bb
Dec 17 2006
prev sibling parent Sean Kelly <sean f4.ca> writes:
Hasan Aljudy wrote:
 I've recently ran across a not-so-convenient behavior of overloading of 
 functions, or rather, of function templates.
 Before I go into details, I'd like to say that I know this behavior 
 complies to the specs .. so please don't reply by saying "this is the 
 intended behaviour!!!", I already know that.
 
 So, what am I talking about?
 
 suppose you have a function
 
 void func( int x ) { ... }
 
 and, say you wanted to overload it with
 
 void func( char[] x ) { ... }
 
 So far so good.
 but, if you try to overload it with a templated function:
 
 void func(T)() { ... }
 
 woops!! template "func" conflicts with "func"!!
 
 Problem: If you want to overload a function to take a "Type" as a 
 parameter, you can't, because func(T)() is not a function, but a 
 template with a function inside it, and, the template symbol name 
 conflicts with the other "func" functions.

So make all three template functions: void func()( int x ) { ... } void func(Dummy1=void, Dummy2=void)( char[] x ) { ... } void func(T)() { ... } Since these all must be in the same module to overload one another anyway, it's not like we'll have situations where users will try to provide overloads for library functions. Sean
Dec 18 2006