在构造函数中使用call()时,与'this'关键字混淆

时间:2018-02-07 09:18:43

标签: javascript

我已经知道call()会将this关键字与目标对象绑定,但我对如何在构造函数中优雅地使用call()感到困惑:

示例代码为:

 function Test(x,y){
	this.x = x;
	this.y = y;
	this.calc = (term)=>{
		console.log(term  + (this.x + this.y));
	}
	this.result = () =>{
		let resultA = {
			x:this.x * 20,
			y:this.y * 20
		}

		this.calc.call(resultA,'the result is ');
	}
    }

    var mytest = new Test(20,20);
    
    mytest.result(); //return 'the result is 40' but was expected to be 800

this.calc()方法意味着多次调用this.result()内声明的不同对象,但它没有按预期工作,所以我的问题是:

  1. 在致电this.calc.call(resultA);时,this.xthis.y值与resultA.xresultA.y无约束力,我想知道为什么会这样?< / p>

  2. 在构造函数中使用call()apply()方法有什么优雅方式吗?

1 个答案:

答案 0 :(得分:2)

您的问题是您正在使用箭头函数,其中postAjax 词汇绑定到封闭范围内的版本,而不是通过第一个参数动态分配到 // Main ajax function using callback for posting data to the server function postAjax( sUrl , frmData, callback ){ /*code*/ callback( ajDataFromServer ); /*code*/ } //using first set of message functions btnSignupForm.addEventListener("click", function (e) { postAjax( "api_signup_users.php", frmSignup, function(data){ signupUser(data, showSuccessMessage, showErrorMessage); }); }); //using second set for another button btnSignupForm2.addEventListener("click", function (e) { postAjax( "api_signup_users.php", frmSignup, function(data){ signupUser(data, showSuccessMessage2, showErrorMessage2); }); }); function signupUser( ajUserDataFromServer, showSuccessMessage, showErrorMessage ) { /*code*/ } function showSuccessMessage ( sSuccessMessage ) { /*code*/ } function showErrorMessage (sErrorMessage) { /*code*/ } function showSuccessMessage2 ( sSuccessMessage ) { /*code*/ } function showErrorMessage2 (sErrorMessage) { /*code*/ }

  // Main ajax function using callback for posting data to the server
  // it still sends only the data to its callback
  function postAjax( sUrl , frmData, callback ){
      /*code*/
      callback( ajDataFromServer );
      /*code*/                
  }

  //using default set of message functions:
  //just pass the function to use as you did in original code, no need for
  //an anonymous function. This function will be passed only the data (cf postAjax code),
  //and because 2 arguments are missing in its definition, it will use its default ones:
  btnSignupForm.addEventListener("click", function (e) {
      postAjax( "api_signup_users.php", frmSignup, signupUser);
  });

  //redefining the message callbacks:
  //the trick here is to use an anonymous function like in precedent code.
  //It is this anonymous function that will be called by postAjax. But now
  //we manually make the call to signupUser inside, so we can decide to use
  //another set of message callbacks by filling the 2nd and 3rd parameters:
  btnSignupForm2.addEventListener("click", function (e) {
      postAjax( "api_signup_users.php", frmSignup, function(data) {
          signupUser(data, showSuccessMessage2, showErrorMessage2);
      });
  });

  function signupUser( ajUserDataFromServer, showSuccessMessageParam, showErrorMessageParam ) {
      //fixed default values for the message functions:
      if(undefined === showSuccessMessageParam){
          showSuccessMessageParam = showSuccessMessage;
      }
      if(undefined === showErrorMessageParam){
          showErrorMessageParam = showErrorMessage;
      }
      /*code*/
      //rest of the code will use the param variables:
      if(isSuccess){
          showSuccessMessageParam('...');
      }else{
          showErrorMessageParam('...');
      }
  }

  function showSuccessMessage ( sSuccessMessage ) {
      /*code*/
  }
  function showErrorMessage (sErrorMessage) {
      /*code*/
  }

  function showSuccessMessage2 ( sSuccessMessage ) {
      /*code*/
  }
  function showErrorMessage2 (sErrorMessage) {
      /*code*/
  }

要获得您想要的行为,您必须将this定义为“普通”功能。