문제
"for… in"루프는 hashtables/elents를 통해 선언 된 순서대로 JavaScript 루프의 루프입니까? 순서대로하지 않는 브라우저가 있습니까?
내가 사용하고 싶은 객체가 선언 될 것입니다 한 번 그리고 결코 수정되지 않습니다.
내가 가지고 있다고 가정 해 봅시다 :
var myObject = { A: "Hello", B: "World" };
그리고 나는 그것들을 추가로 사용합니다.
for (var item in myObject) alert(item + " : " + myObject[item]);
'A : "Hello"'가 항상 가장 괜찮은 브라우저에서 "B :"World "앞에 오기를 기대할 수 있습니까?
해결책
현재 모든 주요 브라우저는 객체의 속성을 정의 한 순서대로 반복합니다. 크롬은 몇 가지 경우를 제외하고는이 작업을 수행합니다. [...]이 동작은 ECMAScript 사양에 의해 명시 적으로 정의되지 않습니다. ECMA-262, 섹션 12.6.4 :
속성 열거의 역학은 ... 구현에 따라 다릅니다.
그러나 사양은 구현과는 상당히 다릅니다. ECMAScript의 모든 최신 구현은 정의 된 순서로 객체 속성을 통해 반복됩니다. 이로 인해 크롬 팀은 이것이 버그로 간주되어 고칠 것입니다.
모든 브라우저는 정의 순서를 존중합니다 크롬을 제외하고 및 모든 비 수수께끼 속성 이름에 대해 수행하는 오페라. 이 두 브라우저에서는 속성이 최초의 비수막 자산보다 앞서 나오게됩니다 (이것은 배열 구현 방법과 관련이 있습니다). 주문은 동일합니다 Object.keys
또한.
이 예제는 다음과 같은 일을 분명히해야합니다.
var obj = {
"first":"first",
"2":"2",
"34":"34",
"1":"1",
"second":"second"
};
for (var i in obj) { console.log(i); };
// Order listed:
// "1"
// "2"
// "34"
// "first"
// "second"
이것의 기술은 이것이 언제라도 변할 수 있다는 사실보다 덜 중요합니다. 이런 식으로 머무르는 것에 의존하지 마십시오.
요컨대 : 주문이 중요한 경우 배열을 사용하십시오.
다른 팁
1 년 후에 이것을 부딪칩니다 ...
그것은이다 2012 그리고 주요 브라우저 아직 다르다:
function lineate(obj){
var arr = [], i;
for (i in obj) arr.push([i,obj[i]].join(':'));
console.log(arr);
}
var obj = { a:1, b:2, c:3, "123":'xyz' };
/* log1 */ lineate(obj);
obj.a = 4;
/* log2 */ lineate(obj);
delete obj.a;
obj.a = 4;
/* log3 */ lineate(obj);
요점 또는 현재 브라우저에서 테스트
사파리 5, 파이어 폭스 14
["a:1", "b:2", "c:3", "123:xyz"]
["a:4", "b:2", "c:3", "123:xyz"]
["b:2", "c:3", "123:xyz", "a:4"]
Chrome 21, Opera 12, Node 0.6, Firefox 27
["123:xyz", "a:1", "b:2", "c:3"]
["123:xyz", "a:4", "b:2", "c:3"]
["123:xyz", "b:2", "c:3", "a:4"]
IE9
[123:xyz,a:1,b:2,c:3]
[123:xyz,a:4,b:2,c:3]
[123:xyz,a:4,b:2,c:3]
로부터 ecmascript 언어 사양, 섹션 12.6.4 (on for .. in
고리):
속성 열거의 역학은 구현에 따라 다릅니다. 열거 순서는 객체에 의해 정의됩니다.
4.3.3 절 ( "개체"의 정의) :
각각은 원시적 값, 물체 또는 함수를 포함하는 순서가없는 속성 모음입니다. 객체의 속성에 저장된 함수를 메소드라고합니다.
JavaScript 구현에서 일관된 순서로 열거되는 속성에 의존 할 수 없다는 것을 의미합니다. (어쨌든 언어의 구현 별 세부 사항에 의존하는 것은 좋지 않을 것입니다.)
주문 정의를 원한다면 객체에 액세스하기 전에 정렬하는 키 배열과 같이 정의하는 것을 구현해야합니다.
열거/인의 객체의 요소는 Dontenum 플래그 세트가없는 특성입니다. ECMAScript (일명 JavaScript) 표준은 "객체는 순서가없는 속성 모음"이라고 명시 적으로 말합니다 (참조 http://www.mozilla.org/js/language/e262-3.pdf 섹션 8.6).
모든 JavaScript 구현이 선언 순서로 열거 될 것이라고 가정하는 것은 표준 준수 (즉, 안전)가 아닙니다.
반복 순서는 또한 속성 삭제와 관련하여 혼동되지만이 경우 IE만으로는 혼동됩니다.
var obj = {};
obj.a = 'a';
obj.b = 'b';
obj.c = 'c';
// IE allows the value to be deleted...
delete obj.b;
// ...but remembers the old position if it is added back later
obj.b = 'bb';
for (var p in obj) {
alert(obj[p]); // in IE, will be a, bb, then c;
// not a, c, then bb as for FF/Chrome/Opera/Safari
}
반복 순서를 수정하기 위해 사양을 변경하려는 욕구는 http://code.google.com/p/v8/issues/detail?id=164 징후입니다.
IE6에서는 주문이 보장되지 않습니다.
주문은 신뢰할 수 없습니다. 오페라와 크롬은 모두 속성 목록을 정렬하지 않게 반환합니다.
<script type="text/javascript">
var username = {"14719":"A","648":"B","15185":"C"};
for (var i in username) {
window.alert(i + ' => ' + username[i]);
}
</script>
위의 코드는 Opera의 B, A, C 및 Chrome의 C, A, B를 보여줍니다.
이것은 질문 자체에 답하지 않지만 기본 문제에 대한 해결책을 제공합니다.
보존하기 위해 의존 할 수 없다고 가정하면 키와 값을 가진 객체 배열을 속성으로 사용하지 않는 이유는 무엇입니까?
var myArray = [
{
'key' : 'key1'
'value' : 0
},
{
'key' : 'key2',
'value' : 1
} // ...
];
이제 키가 고유한지 확인하는 것은 당신에게 달려 있습니다 (이것이 당신에게도 중요하다고 가정합니다. 또한 변경 사항을 직접 해결하고 (... in ...) 이제 인덱스를 '키'로 반환합니다.
> console.log(myArray[0].key);
key1
> for (let index in myArray) {console.log(myArray[index].value);}
0
1
펜을 참조하십시오 (... in ...) 순서대로 JDQ에 의해@JDQ) 에 코데 펜.