var self = this?

后端 未结 8 1403
失恋的感觉
失恋的感觉 2020-11-22 09:10

Using instance methods as callbacks for event handlers changes the scope of this from \"My instance\" to \"Whatever just called the callback\"

相关标签:
8条回答
  • 2020-11-22 09:31

    Yeah, this appears to be a common standard. Some coders use self, others use me. It's used as a reference back to the "real" object as opposed to the event.

    It's something that took me a little while to really get, it does look odd at first.

    I usually do this right at the top of my object (excuse my demo code - it's more conceptual than anything else and isn't a lesson on excellent coding technique):

    function MyObject(){
      var me = this;
    
      //Events
      Click = onClick; //Allows user to override onClick event with their own
    
      //Event Handlers
      onClick = function(args){
        me.MyProperty = args; //Reference me, referencing this refers to onClick
        ...
        //Do other stuff
      }
    }
    
    0 讨论(0)
  • 2020-11-22 09:40

    This question is not specific to jQuery, but specific to JavaScript in general. The core problem is how to "channel" a variable in embedded functions. This is the example:

    var abc = 1; // we want to use this variable in embedded functions
    
    function xyz(){
      console.log(abc); // it is available here!
      function qwe(){
        console.log(abc); // it is available here too!
      }
      ...
    };
    

    This technique relies on using a closure. But it doesn't work with this because this is a pseudo variable that may change from scope to scope dynamically:

    // we want to use "this" variable in embedded functions
    
    function xyz(){
      // "this" is different here!
      console.log(this); // not what we wanted!
      function qwe(){
        // "this" is different here too!
        console.log(this); // not what we wanted!
      }
      ...
    };
    

    What can we do? Assign it to some variable and use it through the alias:

    var abc = this; // we want to use this variable in embedded functions
    
    function xyz(){
      // "this" is different here! --- but we don't care!
      console.log(abc); // now it is the right object!
      function qwe(){
        // "this" is different here too! --- but we don't care!
        console.log(abc); // it is the right object here too!
      }
      ...
    };
    

    this is not unique in this respect: arguments is the other pseudo variable that should be treated the same way — by aliasing.

    0 讨论(0)
  • 2020-11-22 09:40

    If you are doing ES2015 or doing type script and ES5 then you can use arrow functions in your code and you don't face that error and this refers to your desired scope in your instance.

    this.name = 'test'
    myObject.doSomething(data => {
      console.log(this.name)  // this should print out 'test'
    });
    
    0 讨论(0)
  • 2020-11-22 09:40

    I haven't used jQuery, but in a library like Prototype you can bind functions to a specific scope. So with that in mind your code would look like this:

     $('#foobar').ready('click', this.doSomething.bind(this));
    

    The bind method returns a new function that calls the original method with the scope you have specified.

    0 讨论(0)
  • 2020-11-22 09:45
    var functionX = function() {
      var self = this;
      var functionY = function(y) {
        // If we call "this" in here, we get a reference to functionY,
        // but if we call "self" (defined earlier), we get a reference to function X.
      }
    }
    

    edit: in spite of, nested functions within an object takes on the global window object rather than the surrounding object.

    0 讨论(0)
  • 2020-11-22 09:46

    One solution to this is to bind all your callback to your object with javascript's bind method.

    You can do this with a named method,

    function MyNamedMethod() {
      // You can now call methods on "this" here 
    }
    
    doCallBack(MyNamedMethod.bind(this)); 
    

    Or with an anonymous callback

    doCallBack(function () {
      // You can now call methods on "this" here
    }.bind(this));
    

    Doing these instead of resorting to var self = this shows you understand how the binding of this behaves in javascript and doesn't rely on a closure reference.

    Also, the fat arrow operator in ES6 basically is the same a calling .bind(this) on an anonymous function:

    doCallback( () => {
      // You can reference "this" here now
    });
    
    0 讨论(0)
提交回复
热议问题