2014-11-08 2 views
0

콜백에서 부모 범위에 어떻게 액세스합니까? 콜백은 function (err, obj)입니다. var to_user_id는 모든 반복에서 동일합니다. 모든 반복이 완료된 후에 콜백이 처리되는 것처럼 보이므로 var to_user_id는 모든 콜백에 대해 하나의 값일뿐입니다.Javascript (NodeJS) 콜백 범위

for(var i = 0, len = keys.length; i < len; i++) { 

    to_user_id = keys[i].replace('m', '') 

    client.get(keys[i], function (err, obj) { 
    //var not updating, why is both to_user_id=77 
    console.log("match: to_user_id=" + to_user_id + " from_user_id=" + obj) 
    var match = "match: to_user_id=" + to_user_id + " from_user_id=" + obj 
    io.emit(1, match); 
    }); 

} 

출력

는 to_user_id 모두 반복 77 방법을 참조하십시오. 하나는 6해야하며 마지막으로해야 77

경기 : to_user_id = 77 from_user_id = 77

경기 : to_user_id = 77 from_user_id = 6

client.get는 레디 스 기능은 경우에 당신 궁금해하고있어.

답변

1

client.get() 호출은 비동기입니다. 따라서 for 루프는 client.get() 콜백 중 하나가 실행되기 전에 종료됩니다. 즉, client.get() 콜백이 실행될 때까지 to_user_idkeys[keys.length - 1].replace('m', '')으로 설정됩니다. 그래서 당신은 당신의 출력에 같은 to_user_id을보고있는 이유입니다.

여기서 해결 방법은 클로저를 사용하여 현재 값 to_user_id을 캡처하는 것입니다. 이를위한 가장 간단한 방법은 keys.forEach()을 사용하는 것입니다

keys.forEach(function(key) { 
    to_user_id = key.replace('m', '') 

    client.get(key, function (err, obj) { 
    console.log("match: to_user_id=" + to_user_id + " from_user_id=" + obj) 
    var match = "match: to_user_id=" + to_user_id + " from_user_id=" + obj 
    io.emit(1, match); 
    }); 
}); 
+0

아. 클로저는 forEach 내부에 만들어집니다. – nathanengineer

+0

코드가 얼마나 간결했는지 저항 할 수 없어 코드가 사용되었습니다. Javascript는 루비만큼 아름답습니다. – nathanengineer

1

당신이해야하는 i 변수의 값을 저장하기 위해 폐쇄를 만들 수 있습니다.

for (var i = 0, len = 5; i < len; i++) { 
    (function(i, to_user_id) { 
    client.get(i, function(err, obj) { 
     io.emit("match: to_user_id=" + to_user_id + " from_user_id=" + obj) 
    }); 
    }(i, keys[i].replace('m', ''))); 
} 
+0

굉장합니다. 당신은 JS 천재입니다. – nathanengineer