How to get the function name from within that function?

前端 未结 20 896
抹茶落季
抹茶落季 2020-11-22 16:06

How can I access a function name from inside that function?

// parasitic inheritance
var ns.parent.child = function() {
  var parent = new ns.parent();
  p         


        
相关标签:
20条回答
  • 2020-11-22 16:23

    This will work in ES5, ES6, all browsers and strict mode functions.

    Here's how it looks with a named function.

    (function myName() {
      console.log(new Error().stack.split(/\r\n|\r|\n/g)[1].trim());
    })();
    
    at myName (<anonymous>:2:15)
    

    Here's how it looks with an anonymous function.

    (() => {
      console.log(new Error().stack.split(/\r\n|\r|\n/g)[1].trim());
    })();
    
    at <anonymous>:2:15
    
    0 讨论(0)
  • 2020-11-22 16:24

    This might work for you:

    function foo() { bar(); }
    
    function bar() { console.log(bar.caller.name); }
    

    running foo() will output "foo" or undefined if you call from an anonymous function.

    It works with constructors too, in which case it would output the name of the calling constructor (eg "Foo").

    More info here: https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Function/Caller

    They claim it's non-standard, but also that it's supported by all major browsers: Firefox, Safari, Chrome, Opera and IE.

    0 讨论(0)
  • 2020-11-22 16:26

    If I understood what you wanted to do, this is what I do inside a function constructor.

    if (!(this instanceof arguments.callee)) {
        throw "ReferenceError: " + arguments.callee.name + " is not defined";
    }
    
    0 讨论(0)
  • 2020-11-22 16:29

    I had a similar problem and I solved it as follows:

    Function.prototype.myname = function() {
       return this.toString()
           .substr( 0, this.toString().indexOf( "(" ) )
           .replace( "function ", "" ); 
    }
    

    This code implements, in a more comfortable fashion, one response I already read here at the top of this discussion. Now I have a member function retrieving the name of any function object. Here's the full script ...

    <script language="javascript" TYPE="text/javascript">
    
        Function.prototype.myname = function() { 
            return this.toString()
                .substr( 0, this.toString().indexOf( "(" ) )
                .replace("function ", "" ); 
        }
        function call_this( _fn ) { document.write( _fn.myname() ); }
        function _yeaaahhh() { /* do something */ }
        call_this( _yeaaahhh ); 
    
    </script>
    
    0 讨论(0)
  • 2020-11-22 16:29

    you can use Error.stack to trace the function name and exact position of where you are in it.

    See stacktrace.js

    0 讨论(0)
  • 2020-11-22 16:32

    It looks like the most stupid thing, that I wrote in my life, but it's funny :D

    function getName(d){
      const error = new Error();
      const firefoxMatch = (error.stack.split('\n')[0 + d].match(/^.*(?=@)/) || [])[0];
      const chromeMatch = ((((error.stack.split('at ') || [])[1 + d] || '').match(/(^|\.| <| )(.*[^(<])( \()/) || [])[2] || '').split('.').pop();
      const safariMatch = error.stack.split('\n')[0 + d];
    
      // firefoxMatch ? console.log('firefoxMatch', firefoxMatch) : void 0;
      // chromeMatch ? console.log('chromeMatch', chromeMatch) : void 0;
      // safariMatch ? console.log('safariMatch', safariMatch) : void 0;
      
      return firefoxMatch || chromeMatch || safariMatch;
    }
    

    d - depth of stack. 0 - return this function name, 1 - parent, etc.;
    [0 + d] - just for understanding - what happens;
    firefoxMatch - works for safari, but I had really a little time for testing, because mac's owner had returned after smoking, and drove me away :'(

    Testing:

    function limbo(){
      for(let i = 0; i < 4; i++){
        console.log(getName(i));
      }
    }
    function lust(){
      limbo();
    }
    function gluttony(){
      lust();
    }
    
    gluttony();
    

    Result:
    Chrome:

    Fitefox:

    This solution was creating only just for fun! Don't use it for real projects. It does not depend on ES specification, it depends only on browser realization. After the next chrome/firefox/safari update it may be broken.
    More than that there is no error (ha) processing - if d will be more than stack length - you will get an error;
    For other browsers error's message pattern - you will get an error;
    It must work for ES6 classes (.split('.').pop()), but you sill can get an error;

    0 讨论(0)
提交回复
热议问题