www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.bugs - [Issue 5140] New: Add __FUNCTION__

reply d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140

           Summary: Add __FUNCTION__
           Product: D
           Version: unspecified
          Platform: Other
        OS/Version: Linux
            Status: NEW
          Severity: enhancement
          Priority: P2
         Component: DMD
        AssignedTo: nobody puremagic.com
        ReportedBy: jmdavisProg gmx.com


--- Comment #0 from Jonathan M Davis <jmdavisProg gmx.com> 2010-10-30 20:28:59
PDT ---
D has __FILE__ and __LINE__ which give the file and line number where they're
used. C/C++ has those as well, but (at least with some implementations) it also
has __FUNCTION__ which gives the name of the function where it's used, which
can be quite useful (especially when you use it in a logging message, and you
don't necessarily know which version of the program the message comes from).
So, I think that it would be benificial to add __FUNCTION__ to D. Honestly, I
was surprised when it wasn't in the language while __FILE__ and __LINE__ were.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Oct 30 2010
next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


bearophile_hugs eml.cc changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |bearophile_hugs eml.cc


--- Comment #1 from bearophile_hugs eml.cc 2010-10-31 05:56:56 PDT ---
It also allows code like this, this recursive code will keep working even if
"fact" gets renamed, it's more DRY:


long fact(long n) {
    if (n <= 1)
        return 1;
    else
        mixin("return n * " ~ __FUNCTION__ ~ "(n - 1);");
}
void main() {
    assert(fact(20) == 2_432_902_008_176_640_000);
}


But an alias of the current function is more handy for that purpose:

long fact(long n) {
    if (n <= 1)
        return 1;
    else
        return n * __function(n - 1);
}
void main() {
    assert(fact(20) == 2_432_902_008_176_640_000);
}

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Oct 31 2010
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #2 from bearophile_hugs eml.cc 2011-04-16 15:36:18 PDT ---
See a better explanations and some examples of __function:
http://rosettacode.org/wiki/Anonymous_recursion

And I see this is another use case for __function:

http://www.digitalmars.com/webnews/newsgroups.php?art_group=digitalmars.D.learn&article_id=26404

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Apr 16 2011
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Rob T <alanb ucora.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |alanb ucora.com


--- Comment #3 from Rob T <alanb ucora.com> 2012-09-27 00:06:22 PDT ---
I'd like to add that __FUNCTION__ should operate in a consistent manner to
__LINE__ and __FILE__ such that when used as a default value for a function
parameter, the value is set where the function is called, not where the
function is defined.

void Log( string funcname = __FUNCTION__)
{
  writeln( funcname );
}


void func1()
{
  Log(); // displays "func1"
}

void main()
{
  Log(); // displays "main"
}

To be more useful, the nested function names will have to prefixed with parent
level function names, and probably also module name as the highest level.

void main()
{
  void func2()
  {
    Log(); // displays "main.func2"
  }
}

Member functions of class and struc should be prefixed with the class and struc
names respectively.

For templates and overloaded functions, including the function signature would
help resolve which version of a function was called. It may be best to have a
separate version of __FUNCTION__ that displays the function signature, for
example, C++ has __PRETTY_FUNCTION__ which includes the function signature.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Sep 27 2012
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Andrej Mitrovic <andrej.mitrovich gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Keywords|                            |pull
                 CC|                            |andrej.mitrovich gmail.com
            Version|unspecified                 |D2
         AssignedTo|nobody puremagic.com        |andrej.mitrovich gmail.com
         OS/Version|Linux                       |All


--- Comment #4 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-10
19:44:58 PST ---
https://github.com/D-Programming-Language/dmd/pull/1462

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 10 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #5 from bearophile_hugs eml.cc 2013-01-10 20:23:21 PST ---
If __FUNCTION__ gets approved, then probably the probability of __function
getting approved decreases. And I don't care for __FUNCTION__.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 10 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #6 from Rob T <alanb ucora.com> 2013-01-10 23:24:01 PST ---
(In reply to comment #2)
 See a better explanations and some examples of __function:
 http://rosettacode.org/wiki/Anonymous_recursion
 
I really would love to have the ability to perform anonymous recursion. As for the name __FUNCTION__ I don't really like the convention either, but since it is related to __LINE__ and __FILE__, you'd probably have to depreciate those too so as to remain consistent. This is great news if it gets accepted because I need it for log tracing, but I'd also like to see a version of this that displays the full function signature which allows you to see which overload or template version was called. I don't know if the patch does this or not. --rt -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 10 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #7 from Jonathan M Davis <jmdavisProg gmx.com> 2013-01-11 00:05:34
PST ---
__FUNCTION__ is already used by some C/C++ compilers just like __FILE__ and
__LINE__, so there's a fair bit of precedence for it, and it goes well with
__FILE__ and __LINE__.

Personally, I don't care about anonymous recursion and see no need for them,
but I don't see __FUNCTION__ as conflicting with __function at all. They do two
entirely different things. __FUNCTION__ is a string, whereas __function is an
alias to the function that it's used in.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #8 from bearophile_hugs eml.cc 2013-01-11 01:28:47 PST ---
Sorry Andrej, my last comment wasn't a critique of your good work in pull 1462.

(In reply to comment #7)

 but I don't see __FUNCTION__ as conflicting with __function at all. They do two
 entirely different things. __FUNCTION__ is a string, whereas __function is an
 alias to the function that it's used in.
I agree they are two quite different things, so probably I have to move the request for __function in another enhancement request. But they are also related, as you can implement anonymous recursion with __FUNCTION__: long fact(long n) { if (n <= 1) return 1; else mixin("return n * " ~ __FUNCTION__ ~ "(n - 1);"); } So I think introducing __FUNCTION__ will make less likely the introduction of the __function alias. I hope to be wrong.
 Personally, I don't care about anonymous recursion and see no need for them,
Are you using recursion a lot in D? If you never use recursion in D, or you use it only once in thousand lines of code, then you don't have much need for language features that help using recursion, like __func (or private default arguments discussed recently). If you use recursion often, an alias like __func or __function gets useful, because it allows you to write more DRY code, you write the function name only once. So renaming the function or other changes requires you to change only one name. It's like the difference between D OOP and Java, this is Java-like code: class Foo { Foo(int x) {...} void bar(Foo f) { Foo g = new Foo(5); ... } } This is one possible equivalent D code: class Foo { this(int x) {...} void bar(typeof(this) f) { auto g = new typeof(this)(5); ... } } This D code contains the name Foo only once, this is more DRY, and it's useful. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #9 from Jonathan M Davis <jmdavisProg gmx.com> 2013-01-11 01:32:52
PST ---
I simply don't see any need to refer to a function anonymously when making a
recursive call. You can just use its name like you do anywhere else that you
call it. The _only_ advantage that I see is that you have fewer lines of code
to change when you change the function's name, but search and replace takes
care of that quite easily.

I'm not necessarily against the inclusion of __function. I just don't find the
idea useful enough to care.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #10 from bearophile_hugs eml.cc 2013-01-11 01:54:52 PST ---
(In reply to comment #9)
 I simply don't see any need to refer to a function anonymously when making a
 recursive call. You can just use its name like you do anywhere else that you
 call it. The _only_ advantage that I see is that you have fewer lines of code
 to change when you change the function's name, but search and replace takes
 care of that quite easily.
Do you mean you wish/prefer to write OOP like this in D? class Foo { Foo(int x) {...} void bar(Foo f) { Foo g = new Foo(5); ... } } -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Jacob Carlborg <doob me.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |doob me.com


--- Comment #11 from Jacob Carlborg <doob me.com> 2013-01-11 02:33:23 PST ---
(In reply to comment #8)
 Sorry Andrej, my last comment wasn't a critique of your good work in pull 1462.
 
 (In reply to comment #7)
 
 but I don't see __FUNCTION__ as conflicting with __function at all. They do two
 entirely different things. __FUNCTION__ is a string, whereas __function is an
 alias to the function that it's used in.
I agree they are two quite different things, so probably I have to move the request for __function in another enhancement request. But they are also related, as you can implement anonymous recursion with __FUNCTION__: long fact(long n) { if (n <= 1) return 1; else mixin("return n * " ~ __FUNCTION__ ~ "(n - 1);"); } So I think introducing __FUNCTION__ will make less likely the introduction of the __function alias. I hope to be wrong.
Can't __FUNCTION__ be implemented like this: __traits(identifier, __function); That is, if __function gets implemented. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #12 from Don <clugdbug yahoo.com.au> 2013-01-11 04:52:46 PST ---
(In reply to comment #11)
 (In reply to comment #8)
 Sorry Andrej, my last comment wasn't a critique of your good work in pull 1462.
 
 (In reply to comment #7)
 
 but I don't see __FUNCTION__ as conflicting with __function at all. They do two
 entirely different things. __FUNCTION__ is a string, whereas __function is an
 alias to the function that it's used in.
I agree they are two quite different things, so probably I have to move the request for __function in another enhancement request. But they are also related, as you can implement anonymous recursion with __FUNCTION__: long fact(long n) { if (n <= 1) return 1; else mixin("return n * " ~ __FUNCTION__ ~ "(n - 1);"); } So I think introducing __FUNCTION__ will make less likely the introduction of the __function alias. I hope to be wrong.
Can't __FUNCTION__ be implemented like this: __traits(identifier, __function); That is, if __function gets implemented.
No. It needs magical treatment when used as a default parameter. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #13 from Jacob Carlborg <doob me.com> 2013-01-11 05:02:28 PST ---
(In reply to comment #12)

 No. It needs magical treatment when used as a default parameter.
Right, didn't think of that. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #14 from Rob T <alanb ucora.com> 2013-01-11 09:29:13 PST ---
(In reply to comment #10)
 (In reply to comment #9)
 I simply don't see any need to refer to a function anonymously when making a
 recursive call. You can just use its name like you do anywhere else that you
 call it. The _only_ advantage that I see is that you have fewer lines of code
 to change when you change the function's name, but search and replace takes
 care of that quite easily.
Do you mean you wish/prefer to write OOP like this in D? class Foo { Foo(int x) {...} void bar(Foo f) { Foo g = new Foo(5); ... } }
Good points. I know what you say is true because I use recursion often enough to see the advantages. The case for private default args is another solid argument. More generically speaking however, rather than being ad-hoc less-than-useful, what is being proposed actually makes some of D's features more consistent with the rest of D. For example the use of private args is more consistent with the rest of D's features that already have private, such as structs, classes, and modules. Disallowing private args is actually less consistent with the rest of D and is a throw-back to the C era. The _function is actually consistent with the use of "this" for structs and classes. Had these private args and anonymous recursion been implemented from the start, the thought of removing them would never be considered. If we had the chance to redesign D, we could actually make it simpler to use and more powerful by making it more consistent. --rt -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #15 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-11
10:04:38 PST ---
The pull now implements __FUNCTION__ and __PRETTY_FUNCTION__. You can take a
look at the test-case for examples, but in short:

1) __FUNCTION__ as a statement inside a function => fully-qualified name of the
current function
2) __FUNCTION__ as a default init for a parameter => fully-qualified name of
the calling function

3) __PRETTY_FUNCTION__ as a statement inside a function => same as #1 +
parameters, return type, and modifiers.

4) __PRETTY_FUNCTION__ as a default init for a parameter => same as #2 +
parameters, return type, and modifiers.

If either of these is called in module scope (e.g. enum which is initialized
with UFCS), it will return an empty string.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #16 from bearophile_hugs eml.cc 2013-01-11 10:28:43 PST ---
(In reply to comment #15)

 If either of these is called in module scope (e.g. enum which is initialized
 with UFCS), it will return an empty string.
A question: isn't it better to give a compilation error in this case, instead of returning an empty result? -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #17 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-11
12:31:38 PST ---
(In reply to comment #16)
 (In reply to comment #15)
 
 If either of these is called in module scope (e.g. enum which is initialized
 with UFCS), it will return an empty string.
A question: isn't it better to give a compilation error in this case, instead of returning an empty result?
No, because it would make the function unusable in CTFE in some contexts. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Andrej Mitrovic <andrej.mitrovich gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
            Summary|Add __FUNCTION__ and        |Add __FUNCTION__,
                   |__PRETTY_FUNCTION__         |__PRETTY_FUNCTION__, and
                   |                            |__MODULE__


--- Comment #18 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-11
16:36:57 PST ---
The enhancemented now includes __MODULE__ as requested by Andrei and others.

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Andrej Mitrovic <andrej.mitrovich gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |georg iki.fi


--- Comment #19 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-11
19:39:54 PST ---
*** Issue 2909 has been marked as a duplicate of this issue. ***

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Jan 11 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #20 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-12
10:28:13 PST ---
(In reply to comment #8)
 entirely different things. __FUNCTION__ is a string, whereas __function is an
 alias to the function that it's used in.
I agree they are two quite different things, so probably I have to move the request for __function in another enhancement request.
Please make another enhancement request for this, so it's not forgotten and we can wait for a separate approval. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 12 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #21 from Andrej Mitrovic <andrej.mitrovich gmail.com> 2013-01-12
10:42:15 PST ---
(In reply to comment #8)
 But they are also related, as you can implement anonymous recursion with
 __FUNCTION__:
 
 
 long fact(long n) {
     if (n <= 1)
         return 1;
     else
         mixin("return n * " ~ __FUNCTION__ ~ "(n - 1);");
 }
This is unreliable. If `fact` is nested inside of a mixin template you won't be able to call the function this way. On another note this has uncovered a new ICE in Issue 9182. It's also very untidy to have to use mixins and string representation for recursive calls. It's much simpler to use 'return __function(n - 1)'. -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 12 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #22 from bearophile_hugs eml.cc 2013-01-12 13:47:44 PST ---
(In reply to comment #20)

 Please make another enhancement request for this, so it's not forgotten and we
 can wait for a separate approval.
OK. See Issue 9306 -- Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email ------- You are receiving this mail because: -------
Jan 12 2013
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140



--- Comment #23 from github-bugzilla puremagic.com 2013-03-06 20:02:48 PST ---
Commits pushed to master at https://github.com/D-Programming-Language/dmd

https://github.com/D-Programming-Language/dmd/commit/1822acb7a47ae71c3889db2c26efbfb7d1c64c5c
Fixes Issue 5140 - Implement __FUNCTION__, __PRETTY_FUNCTION__, and
__MODULE__ feature.

https://github.com/D-Programming-Language/dmd/commit/fd628d8170730cf01f318e1b15e0d894be358f17
Merge pull request #1462 from AndrejMitrovic/Fix5140

[enh] Issue 5140 - Implement __FUNCTION__, __PRETTY_FUNCTION__ and __MODULE__

-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Mar 06 2013
prev sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=5140


Andrej Mitrovic <andrej.mitrovich gmail.com> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|NEW                         |RESOLVED
         Resolution|                            |FIXED


-- 
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
Mar 07 2013