2009-12-30 5 views
2

안녕하세요, 다음 JavaScript 코드를 실행하려고합니다. 제 목표는 JavaScript의 다양한 범위와 호출 유형에서 this의 의미를 파악하는 것입니다.JavaScript의 "this"객체와 혼동 익명 함수

아래 코드를 보면 : 나는 내부 익명 함수를 가지고 있는데, 이는 innerStuff 변수에 할당됩니다. 그러한 익명 함수로 thiswindow 개체를 가리키고 외부 함수 개체 또는 다른 것은 아닙니다. 이벤트는 여전히 함수의 변수를 액세스 할 수 있습니다.

어쨌든, 나는 확실하지 않습니다. 아래의 코드를 보시면 that에서 innerStuff 형태로 this을 전달하고 콘솔에서 doofus 속성을 가진 객체를 출력합니다.

var someStuff = { 
     doofus:"whatever", 
     newF: function() 
     { 
      var that = this; 
      console.log(that); 
      var innerStuff = function(topThis){ 
       console.log(topThis); 
      }; 

      return innerStuff(that); 
     } 
    } 

    someStuff.newF(); 

이제 코드를 조금만 변경하려고합니다. 아래 그림과 같이 대신 innerStuff에 할당하는, 난 그냥 직접 호출하는 기능을 돌아갑니다 : 내부 익명 함수에 대한 정의되지 않은

var someStuff = { 
     doofus:"whatever", 
     newF: function() 
     { 
      var that = this; 
      console.log(that); 
      return function(that){ 
       console.log(that); 
      }(); 
     } 
    } 

    someStuff.newF(); 

이 인쇄. 매개 변수로 전달되는 that과 외부 함수로 정의되는 that 사이에 충돌이 발생했기 때문입니까? 매개 변수가 가시성을 재정의했다고 생각했습니다. 가치가 유지되지 않는 이유는 무엇입니까?

이것은 완전히 혼란 스럽습니다.

반면에 that을 전달하지 않고 가시성이 있기 때문에이를 사용하면 예상대로 결과가 적합합니다.

실종 신고는 무엇입니까? 같은 범위에있는 변수 사이의 충돌입니까? 내부 기능에 thiswindow 개체에 바인딩되어 있다는 충분한 이유가 있습니까?

답변

9

this은 자바 스크립트에서 객체를 참조했습니다. 함수를 someObject.functionName(args)으로 호출하면 this이 해당 개체에 바인딩됩니다. functionName(args)처럼 맨손 기능을 호출하는 경우 thiswindow 개체에 바인딩됩니다.

두 번째 예의 newF 안에는 that 변수가 내부 함수에 섀도 잉되어 있지만 아무 것도 전달하지 않으므로 정의되지 않습니다.

 var that = this; 
     console.log(that); 
     return function(that){ 
      console.log(that); 
     }(); 
당신은 아마 원하는

당신이 첫 번째 예에 해당 무언가를 원하는 경우 (내부 기능에 that 전달), 대신 다음

 var that = this; 
     console.log(that); 
     return function(that){ 
      console.log(that); 
     }(that); 

또는 다음, 당신이 돈이 ' t는 그림자와 단지 외부 함수의 바인딩을 사용하려면 : 두 번째 예에서

 var that = this; 
     console.log(that); 
     return function(){ 
      console.log(that); 
     }(); 
+0

아! 내가 그걸 놓쳤다는 것을 믿을 수 없다. 엄청 고마워. – Priyank

+0

글쎄, 바운드 메소드가 바운드 메소드가있는 다른 모든 언어에서 작동하는 방법과 완전히 다르다. – bobince

1

, 당신은 익명 함수를 호출, 매개 변수를 that이 정의되지 않았습니다 (아무 것도 전달하지 않음).) 이것을 할 수 있습니다 :

newF: function() 
    { 
     var that = this; 
     console.log(that); 
     return function(that){ 
      console.log(that); 
     }(that); // note that we are passing our 'that' in as 'that' 
    } 

이렇게하면 변수의 적절한 값을 유지할 수 있습니다. 위 var that 범위를 지정하기 때문에

그러나, 당신은 단지뿐만 아니라 함수 매개 변수를 제거 할 수 있습니다 :

newF: function() 
    { 
     var that = this; 
     console.log(that); 
     return function(){ 
      console.log(that); 
     }(); // 'that' is referenced above. 
    } 

을 지금까지 익명 함수가 같은 window을 왜 그들의 this : 당신은 컨텍스트없이 함수를 호출 할 때마다 (예 : somef()context.somef()) thiswindow 개체를 가리 킵니다.

함수에서 .apply(context, argumentsArray) or .call(context, arg1, arg2, arg3)을 사용하여 this을 전달하고 전달할 수 있습니다. 예 다음 someStuff 객체의 멤버 함수 내에서 선언하지만 첫 번째 코드 예제에서

newF: function() 
    { 
     console.log('Outer:', this); 
     var innerF = function(){ 
      console.log('Inner:', this); 
     }; 
     return innerF.apply(this,arguments); 
    } 
1

는, 익명 함수는의 someStuff 개체의 구성원이 아닙니다. 따라서 해당 함수의 this은 윈도우 객체에 대한 참조입니다. 당신은 익명 함수를 호출하고 this 참조 제어 할 싶었다면, 다음을 수행 할 수 : 당신이 실제로 그것을 실행, 익명 함수를 만들고, 두 번째 예에서

var someStuff = { 
    doofus:"whatever", 
    newF: function() 
    { 
     var that = this; 
     console.log(that); 
     var innerStuff = function(){ 
      console.log(this); 
     }; 

     return innerStuff.apply(this); 
    } 
} 

someStuff.newF(); 

, 다음 값을 반환을 그 익명의 함수가 돌려 주어집니다. 그러나 익명의 함수는 아무 것도 반환하지 않습니다. 또한 변수 이름이 충돌합니다. 당신은 할 수 : 함수는 익명 함수의 반환 값을 반환하는 실행 기능 때문에, 뭔가를 반환해야하기 때문에이 반환 진정한 추가

var someStuff = { 
    doofus:"whatever", 
    newF: function() 
    { 
     var that = this; 
     console.log(that); 
     return function(){ 
      console.log(that); 
      return true; 
     }(); 
    } 
} 

someStuff.newF(); 

. true 또는 false 또는 문자열 또는 객체 또는 그 밖의 시나리오를 반환하는지 여부

+0

"적용"호출을 사용할 수 있지만 첫 번째 요점에 동의한다. 두 번째 요점은 잘못되었다. 전달 된 매개 변수가 외부 함수의 param을 재정의하므로 이름 충돌이 없습니다. 내가 한 실수는 호출하는 동안 익명의 함수에 param을 전달하지 않았다는 것입니다. [위의 예제에서 Brian이 보여준 바와 같이] 그는 제안 된 솔루션이 잘 작동하여 문제가 해결되었습니다. 반환 값은, 나는 너무 많이 돌 보았다고 생각하지 않는다. 이 값의 가치가 내부 함수 내에서 어떻게 범위 지워지는지보고 싶었습니다. 도움 주셔서 감사합니다. – Priyank