JavaScript 개체를 반복하거나 열거하려면 어떻게 해야 합니까?
-
22-08-2019 - |
문제
다음과 같은 JavaScript 개체가 있습니다.
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
이제 모든 것을 반복하고 싶습니다. p
요소(p1
, p2
, p3
...) 그리고 해당 키와 값을 가져옵니다.어떻게 해야 합니까?
필요한 경우 JavaScript 개체를 수정할 수 있습니다.내 궁극적인 목표는 일부 키 값 쌍을 반복하는 것이며 가능하면 사용을 피하고 싶습니다. eval
.
해결책
당신은 사용할 수 있습니다 for-in
다른 사람들이 보여주는 루프. 그러나, 당신은 당신이 얻는 키가 객체의 실제 속성이며, 프로토 타입에서 나오지 않도록해야합니다.
스 니펫은 다음과 같습니다.
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
for (var key in p) {
if (p.hasOwnProperty(key)) {
console.log(key + " -> " + p[key]);
}
}
다른 팁
ECMAScript 5에서는 결합 할 수 있습니다 Object.keys()
그리고 Array.prototype.forEach()
:
var obj = { first: "John", last: "Doe" };
Object.keys(obj).forEach(function(key) {
console.log(key, obj[key]);
});
ECMAScript 6 추가 for...of
:
for (const key of Object.keys(obj)) {
console.log(key, obj[key]);
}
ECMAScript 8 추가 Object.entries()
원래 객체에서 각 값을 찾지 않아도됩니다.
Object.entries(obj).forEach(
([key, value]) => console.log(key, value)
);
당신은 결합 할 수 있습니다 for...of
, 파괴 및 Object.entries
:
for (const [key, value] of Object.entries(obj)) {
console.log(key, value);
}
둘 다 Object.keys()
그리고 Object.entries()
동일한 순서로 속성을 반복하십시오 for...in
고리 그러나 프로토 타입 체인을 무시하십시오. 객체 자체의 열거 가능한 속성 만 반복됩니다.
당신은 그것을 사용해야합니다 for-in loop
그러나 이런 종류의 루프를 사용할 때 매우 조심하십시오. 프로토 타입 체인을 따라 모든 특성을 루프하십시오.
따라서 For-in 루프를 사용할 때는 항상 hasOwnProperty
반복의 현재 속성이 실제로 확인하는 객체의 속성인지 확인하는 방법 :
for (var prop in p) {
if (!p.hasOwnProperty(prop)) {
//The current property is not a direct property of p
continue;
}
//Do your logic with the property here
}
객체를 통과하는 대체 방법에 대해 언급하지 않으면 문제가 완료되지 않습니다.
오늘날 잘 알려진 많은 JavaScript 라이브러리는 컬렉션을 반복하기위한 자체 방법을 제공합니다. 배열, 사물, 그리고 어레이와 같은 객체. 이 방법은 사용하기 편리하며 모든 브라우저와 전적으로 호환됩니다.
당신이 함께 일한다면 jQuery, 당신은 사용할 수 있습니다
jQuery.each()
방법. 객체와 배열을 모두 원활하게 반복하는 데 사용될 수 있습니다.$.each(obj, function(key, value) { console.log(key, value); });
~ 안에 aUNDSCORE.JS 방법을 찾을 수 있습니다
_.each()
, 요소 목록을 반복하여 각각 공급 된 기능으로 각각을 산출합니다 (인수 순서에주의를 기울이십시오. 반복 기능!):_.each(obj, function(value, key) { console.log(key, value); });
로마 객체 속성을 반복하기위한 몇 가지 방법을 제공합니다. 기초적인
_.forEach()
(또는 별명입니다_.each()
) 그러나 객체와 배열 모두를 통해 반복하는 데 유용하지만 (!) 객체length
속성은 배열처럼 취급 되며이 동작을 피하기 위해 사용하는 것이 좋습니다._.forIn()
그리고_.forOwn()
방법 (이것들도 가지고 있습니다value
인수가 먼저 다가오는 인수) :_.forIn(obj, function(value, key) { console.log(key, value); });
_.forIn()
반복 자신과 상속 객체의 열거 가능한 특성_.forOwn()
반복 만 반복합니다 소유하다 객체의 속성 (기본적으로 확인hasOwnProperty
기능). 간단한 객체와 물체 리터럴의 경우이 방법 중 하나가 잘 작동합니다.
일반적으로 설명 된 모든 방법은 제공된 객체와 동일한 동작을 갖습니다. 네이티브를 사용하는 것 외에 for..in
루프는 보통입니다 더 빠르게 어떤 추상화보다 jQuery.each()
, 이러한 방법은 사용하기 쉽고 코딩이 적고 더 나은 오류 처리를 제공합니다.
ECMAScript 5에는 리터럴 반복 필드에 새로운 접근 방식이 있습니다. Object.keys
자세한 정보를 확인할 수 있습니다 MDN
내 선택은 현재 버전의 브라우저에서 더 빠른 솔루션으로 아래에 있습니다 (Chrome30, IE10, FF25)
var keys = Object.keys(p),
len = keys.length,
i = 0,
prop,
value;
while (i < len) {
prop = keys[i];
value = p[prop];
i += 1;
}
이 접근법의 성능을 다른 구현과 비교할 수 있습니다. jsperf.com:
브라우저 지원을 볼 수 있습니다 Kangax의 호환 테이블
upd :
이 질문에서 가장 인기있는 모든 사례에 대한 성능 비교 perfjs.info
:
당신은 다음과 같이 반복 할 수 있습니다.
for (var key in p) {
alert(p[key]);
}
주목하십시오 key
속성의 가치를 취하지 않고 인덱스 값 일뿐입니다.
머리말:
- 객체 속성이 될 수 있습니다 소유하다 (속성은 객체 자체에 있습니다) 또는 상속 (객체 자체가 아니라 프로토 타입 중 하나에 있습니다).
- 객체 속성이 될 수 있습니다 열거 가능 또는 나누기가 불가능합니다. 많은 속성 열거/어레이에서 나온 속성이 나오지 않습니다.
- 속성 이름은 문자열 또는 기호 일 수 있습니다. 이름이 상징 인 속성의 속성은 많은 속성 열거/배열에서 제외됩니다.
2018 년에는 객체의 속성을 통한 반복 옵션이 있습니다 (일부 예제는 목록을 따릅니다).
for-in
[MDN, 투기] - 객체의 이름을 통해 루프하는 루프 구조 열거 가능 상속 된 것들을 포함하여 속성, 이름은 문자열입니다.Object.keys
[MDN, 투기] - 객체 이름의 배열을 제공하는 함수 소유하다, 열거 가능 이름이 문자열 인 속성.Object.values
[MDN, 투기] - 배열을 제공하는 함수 가치 물체의 소유하다, 열거 가능 속성.Object.entries
[MDN, 투기] - 이름의 배열을 제공하는 함수 그리고 객체의 값 소유하다, 열거 가능 속성 (배열의 각 항목은 a[name, value]
정렬).Object.getOwnPropertyNames
[MDN, 투기] - 객체 이름의 배열을 제공하는 함수 소유하다 이름이 줄 인 속성 (심지어 발달 할 수없는 속성).Object.getOwnPropertySymbols
[MDN, 투기] - 객체 이름의 배열을 제공하는 함수 소유하다 이름이 상징 인 속성 (심지어 발달 할 수없는 속성).Reflect.ownKeys
[MDN, 투기] - 객체 이름의 배열을 제공하는 함수 소유하다 그 이름이 문자열이든 상징인지 여부에 관계없이 속성 (심지어 발달 할 수없는 속성).- 네가 원한다면 모두 개체의 속성을 포함하여 상속되지 않은 물체의 속성 중 하나는 루프를 사용해야합니다.
Object.getPrototypeOf
[MDN, 투기] 그리고 사용Object.getOwnPropertyNames
,Object.getOwnPropertySymbols
, 또는Reflect.ownKeys
프로토 타입 체인의 각 객체에서 (이 답변의 하단에있는 예).
그들 모두를 제외하고 for-in
, 당신은 배열에 어떤 종류의 루핑 구조를 사용합니다 (for
, for-of
, forEach
, 등.).
예 :
for-in
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const name in o) {
const value = o[name];
console.log(`${name} = ${value}`);
}
Object.keys
(a for-of
루프이지만 루핑 구조를 사용할 수 있습니다):
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const name of Object.keys(o)) {
const value = o[name];
console.log(`${name} = ${value}`);
}
Object.values
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const value of Object.values(o)) {
console.log(`${value}`);
}
Object.entries
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const [name, value] of Object.entries(o)) {
console.log(`${name} = ${value}`);
}
Object.getOwnPropertyNames
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const name of Object.getOwnPropertyNames(o)) {
const value = o[name];
console.log(`${name} = ${value}`);
}
Object.getOwnPropertySymbols
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const name of Object.getOwnPropertySymbols(o)) {
const value = o[name];
console.log(`${String(name)} = ${value}`);
}
Reflect.ownKeys
:
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (const name of Reflect.ownKeys(o)) {
const value = o[name];
console.log(`${String(name)} = ${value}`);
}
모든 속성, 상속받지 못한 것들을 포함하여 :
// A prototype object to inherit from, with a string-named property
const p = {answer: 42};
// The object we'll look at, which inherits from `p`
const o = Object.create(p);
// A string-named property
o.question = "Life, the Universe, and Everything";
// A symbol-named property
o[Symbol("author")] = "Douglas Adams";
for (let depth = 0, current = o; current; ++depth, current = Object.getPrototypeOf(current)) {
for (const name of Reflect.ownKeys(current)) {
const value = o[name];
console.log(`[${depth}] ${String(name)} = ${String(value)}`);
}
}
.as-console-wrapper {
max-height: 100% !important;
}
ES2015가 점점 더 인기를 얻고 있기 때문에 나는이 답변을 게시하고 있습니다. [key, value]
한 쌍. 예를 들어 루비와 같은 다른 언어로 가능합니다.
좋아 여기 코드가 있습니다.
const MyObject = {
'a': 'Hello',
'b': 'it\'s',
'c': 'me',
'd': 'you',
'e': 'looking',
'f': 'for',
[Symbol.iterator]: function* () {
for (const i of Object.keys(this)) {
yield [i, this[i]];
}
}
};
for (const [k, v] of MyObject) {
console.log(`Here is key ${k} and here is value ${v}`);
}
Developer Mozilla Page에서 찾을 수있는 반복자 및 생성기를 수행 할 수있는 방법에 대한 모든 정보.
누군가가 도움이되기를 바랍니다.
편집하다:
ES2017에는 포함됩니다 Object.entries
반복 할 것입니다 [key, value]
물체의 쌍이 훨씬 더 쉽습니다. 이제는 표준의 일부가 될 것으로 알려져 있습니다. TS39 무대 정보.
나는 그것이 지금보다 훨씬 더 신선하게되도록 내 대답을 업데이트 할 때라고 생각합니다.
const MyObject = {
'a': 'Hello',
'b': 'it\'s',
'c': 'me',
'd': 'you',
'e': 'looking',
'f': 'for',
};
for (const [k, v] of Object.entries(MyObject)) {
console.log(`Here is key ${k} and here is value ${v}`);
}
사용에 대한 자세한 내용은 사용 가능합니다MDN 페이지
for(key in p) {
alert( p[key] );
}
참고 : 배열을 통해이 작업을 수행 할 수 있지만 length
그리고 다른 속성도 있습니다.
여기의 모든 답변을 살펴본 후, json 객체가 깨끗하기 때문에 HasownProperty는 내 사용에 대해 필요하지 않습니다. 추가 JavaScript 처리를 추가하는 것은 의미가 없습니다. 이것은 내가 사용하는 전부입니다.
for (var key in p) {
console.log(key + ' => ' + p[key]);
// key is key
// value is p[key]
}
~을 통해 원기 ~와 함께 각각() 건너 뛰어야합니다 프로토 타입 체인 속성:
Object.prototype.each = function(f) {
var obj = this
Object.keys(obj).forEach( function(key) {
f( key , obj[key] )
});
}
//print all keys and values
var obj = {a:1,b:2,c:3}
obj.each(function(key,value) { console.log(key + " " + value) });
// a 1
// b 2
// c 3
이 답변에서 흥미로운 사람들이 Object.keys()
그리고 for...of
그러나 절대 결합하지 않았습니다.
var map = {well:'hello', there:'!'};
for (let key of Object.keys(map))
console.log(key + ':' + map[key]);
당신은 그냥 할 수 없습니다 for...of
an Object
반복자가 아니기 때문에 for...index
또는 .forEach()
ing Object.keys()
추악/비효율적입니다.
대부분의 사람들이 자제하는 것이 기쁩니다 for...in
(점검 유무에 관계없이 .hasOwnProperty()
) 그게도 약간 지저분하므로 위의 대답 외에는 여기에 있습니다 ...
평범한 객체 협회를 반복 할 수 있습니다! 처럼 행동합니다 Map
공상을 직접 사용하는 s for...of
데모 Chrome 및 FF에서 일하는 (ES6 만 가정합니다)
var ordinaryObject = {well:'hello', there:'!'};
for (let pair of ordinaryObject)
//key:value
console.log(pair[0] + ':' + pair[1]);
//or
for (let [key, value] of ordinaryObject)
console.log(key + ':' + value);
아래에 내 심을 포함하는 한 :
//makes all objects iterable just like Maps!!! YAY
//iterates over Object.keys() (which already ignores prototype chain for us)
Object.prototype[Symbol.iterator] = function() {
var keys = Object.keys(this)[Symbol.iterator]();
var obj = this;
var output;
return {next:function() {
if (!(output = keys.next()).done)
output.value = [output.value, obj[output.value]];
return output;
}};
};
좋은 구문 설탕이없는 실제 맵 객체를 만들 필요가 없습니다.
var trueMap = new Map([['well', 'hello'], ['there', '!']]);
for (let pair of trueMap)
console.log(pair[0] + ':' + pair[1]);
사실,이 심의 경우, 여전히지도의 다른 기능을 활용하고 싶다면 (모든 것을 모두 깎지 않고) 깔끔한 객체 표기법을 사용하고 싶었습니다. 이제 객체가 반복되기 때문에 이제 맵을 만들 수 있습니다!
//shown in demo
var realMap = new Map({well:'hello', there:'!'});
심하거나 엉망이되는 것을 좋아하지 않는 사람들을 위해 prototype
일반적으로 창에서 기능을 대신 자유롭게 만들어서 getObjIterator()
그 다음에;
//no prototype manipulation
function getObjIterator(obj) {
//create a dummy object instead of adding functionality to all objects
var iterator = new Object();
//give it what the shim does but as its own local property
iterator[Symbol.iterator] = function() {
var keys = Object.keys(obj)[Symbol.iterator]();
var output;
return {next:function() {
if (!(output = keys.next()).done)
output.value = [output.value, obj[output.value]];
return output;
}};
};
return iterator;
}
이제 당신은 그것을 평범한 기능이라고 부를 수 있습니다.
var realMap = new Map(getObjIterator({well:'hello', there:'!'}))
또는
for (let pair of getObjIterator(ordinaryObject))
미래에 오신 것을 환영합니다.
Object.keys (obj) : 배열
모든 열거 가능한 자체 (비인간) 속성의 모든 문자열 값 키를 검색합니다.
따라서 HasownProperty로 각 객체 키를 테스트하여 의도하는 것과 동일한 키 목록을 제공합니다. 당신은 그보다 추가 테스트 작업이 필요하지 않습니다 Object.keys( obj ).forEach(function( key ){})
더 빠르야합니다. 증명합시다 :
var uniqid = function(){
var text = "",
i = 0,
possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
for( ; i < 32; i++ ) {
text += possible.charAt( Math.floor( Math.random() * possible.length ) );
}
return text;
},
CYCLES = 100000,
obj = {},
p1,
p2,
p3,
key;
// Populate object with random properties
Array.apply( null, Array( CYCLES ) ).forEach(function(){
obj[ uniqid() ] = new Date()
});
// Approach #1
p1 = performance.now();
Object.keys( obj ).forEach(function( key ){
var waste = obj[ key ];
});
p2 = performance.now();
console.log( "Object.keys approach took " + (p2 - p1) + " milliseconds.");
// Approach #2
for( key in obj ) {
if ( obj.hasOwnProperty( key ) ) {
var waste = obj[ key ];
}
}
p3 = performance.now();
console.log( "for...in/hasOwnProperty approach took " + (p3 - p2) + " milliseconds.");
내 파이어 폭스에는 다음과 같은 결과가 있습니다
- Object.keys 접근법은 40.21101451665163 밀리 초를 가져 왔습니다.
- ... IN/HASOWNPROPERTY 접근법은 98.26163508463651 밀리 초를 사용했습니다.
추신. Chrome에서는 차이가 더 큽니다 http://codepen.io/dsheiko/pen/jdrqxa
PS2 : ES6 (ECMAScript 2015)에서 반복 가능한 객체를 더 잘 반복 할 수 있습니다.
let map = new Map().set('a', 1).set('b', 2);
for (let pair of map) {
console.log(pair);
}
// OR
let map = new Map([
[false, 'no'],
[true, 'yes'],
]);
map.forEach((value, key) => {
console.log(key, value);
});
다음은 객체를 통해 반복하는 또 다른 방법입니다.
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
Object.keys(p).forEach(key => { console.log(key, p[key]) })
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
for (var key in p) {
if (p.hasOwnProperty(key)) {
console.log(key + " = " + p[key]);
}
}
<p>
Output:<br>
p1 = values1<br>
p2 = values2<br>
p3 = values3
</p>
그만큼 Object.keys()
메소드는 주어진 객체 자체의 열거 가능한 속성의 배열을 반환합니다. 그것에 대해 자세히 알아보십시오 여기
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
Object.keys(p).map((key)=> console.log(key + "->" + p[key]))
간단한 것을 추가 할 수 있습니다 각각 모든 객체에 기능하므로 모든 객체를 자동으로 고정 할 수 있습니다.
Object.defineProperty(Object.prototype, 'forEach', {
value: function (func) {
for (var key in this) {
if (!this.hasOwnProperty(key)) {
// skip loop if the property is from prototype
continue;
}
var value = this[key];
func(key, value);
}
},
enumerable: false
});
"좋아하지 않는 사람들을 위해"... in"-방법:
Object.defineProperty(Object.prototype, 'forEach', {
value: function (func) {
var arr = Object.keys(this);
for (var i = 0; i < arr.length; i++) {
var key = arr[i];
func(key, this[key]);
}
},
enumerable: false
});
이제 간단한 전화를 할 수 있습니다.
p.forEach (function(key, value){
console.log ("Key: " + key);
console.log ("Value: " + value);
});
다른 foreach-methods와 충돌하고 싶지 않다면 독특한 이름으로 이름을 지정할 수 있습니다.
종속성이없는 JavaScript 코드 만 :
var p = {"p1": "value1", "p2": "value2", "p3": "value3"};
keys = Object.keys(p); // ["p1", "p2", "p3"]
for(i = 0; i < keys.length; i++){
console.log(keys[i] + "=" + p[keys[i]]); // p1=value1, p2=value2, p3=value3
}
루프는 순수 JavaScript를 사용할 때 꽤 흥미로울 수 있습니다.ECMA6(New 2015 JavaScript 사양)만이 루프를 제어할 수 있는 것 같습니다.불행하게도 제가 이 글을 쓰고 있는 동안에는 브라우저와 널리 사용되는 통합 개발 환경(IDE) 모두 새로운 부가 기능을 완전히 지원하기 위해 여전히 고군분투하고 있습니다.
ECMA6 이전의 JavaScript 객체 루프는 다음과 같습니다.
for (var key in object) {
if (p.hasOwnProperty(key)) {
var value = object[key];
console.log(key); // This is the key;
console.log(value); // This is the value;
}
}
또한 나는 이것이 이 질문의 범위를 벗어난다는 것을 알고 있지만 2011년에 ECMAScript 5.1은 forEach
기본적으로 배열을 반복하는 새로운 향상된 방법을 만든 배열 전용 메서드는 여전히 반복할 수 없는 개체를 이전의 장황하고 혼란스러운 상태로 남겨 둡니다. for
고리.그런데 이상한 점은 이 새로운 forEach
메소드는 지원하지 않습니다 break
그로 인해 온갖 종류의 문제가 발생했습니다.
기본적으로 2011년에는 많은 인기 라이브러리(jQuery, Underscore 등)가 다시 구현하기로 결정한 것 외에는 JavaScript에서 루프를 수행할 수 있는 확실한 방법이 없습니다.
2015년부터 우리는 이제 모든 객체 유형(배열 및 문자열 포함)을 루프(및 중단)할 수 있는 더 나은 기본 방법을 갖게 되었습니다.권장사항이 주류가 되었을 때 JavaScript의 루프는 다음과 같습니다.
for (let [key, value] of Object.entries(object)) {
console.log(key); // This is the key;
console.log(value); // This is the value;
}
2016년 6월 18일 현재 대부분의 브라우저는 위 코드를 지원하지 않습니다.Chrome에서도 작동하려면 이 특수 플래그를 활성화해야 합니다. chrome://flags/#enable-javascript-harmony
이것이 새로운 표준이 될 때까지 이전 방법을 계속 사용할 수 있지만 인기 있는 라이브러리나 심지어는 대안도 있습니다. 경량 대안 이 라이브러리를 사용하지 않는 사람들을 위해.
var p =[{"username":"ordermanageadmin","user_id":"2","resource_id":"Magento_Sales::actions"},
{"username":"ordermanageadmin_1","user_id":"3","resource_id":"Magento_Sales::actions"}]
for(var value in p) {
for (var key in value) {
if (p.hasOwnProperty(key)) {
console.log(key + " -> " + p[key]);
}
}
}
누군가가 반복 해야하는 경우 조건이있는 ArrayObjects:
var arrayObjects = [{"building":"A", "status":"good"},{"building":"B","status":"horrible"}];
for (var i=0; i< arrayObjects.length; i++) {
console.log(arrayObjects[i]);
for(key in arrayObjects[i]) {
if (key == "status" && arrayObjects[i][key] == "good") {
console.log(key + "->" + arrayObjects[i][key]);
}else{
console.log("nothing found");
}
}
}
ES6을 고려할 때 나는 나만의 설탕 숟가락을 추가하고 물체의 특성을 반복하기위한 한 가지 더 접근하고 싶습니다.
일반 JS 객체는 그렇지 않기 때문입니다 반복적 인 상자 밖에서 우리는 사용할 수 없습니다. for..of
콘텐츠를 반복하기위한 루프. 그러나 아무도 우리를 막을 수 없습니다 반복하기 위해.
우리에게 가자 book
물체.
let book = {
title: "Amazing book",
author: "Me",
pages: 3
}
book[Symbol.iterator] = function(){
let properties = Object.keys(this); // returns an array with property names
let counter = 0;
let isDone = false;
let next = () => {
if(counter >= properties.length){
isDone = true;
}
return { done: isDone, value: this[properties[counter++]] }
}
return { next };
}
우리는 그것을 만들었 기 때문에 이런 식으로 사용할 수 있습니다.
for(let pValue of book){
console.log(pValue);
}
------------------------
Amazing book
Me
3
또는 ES6의 힘을 알고 있다면 발전기, 당신은 확실히 코드를 훨씬 더 짧게 만들 수 있습니다.
book[Symbol.iterator] = function *(){
let properties = Object.keys(this);
for (let p of properties){
yield this[p];
}
}
물론, 당신은 모든 대상에 그러한 행동을 적용 할 수 있습니다. Object
반복적 인 prototype
수준.
Object.prototype[Symbol.iterator] = function() {...}
또한 반복 가능한 프로토콜을 준수하는 객체는 새로운 ES2015 기능과 함께 사용할 수 있습니다. 확산 따라서 연산자는 객체 속성 값을 배열로 읽을 수 있습니다.
let pValues = [...book];
console.log(pValues);
-------------------------
["Amazing book", "Me", 3]
또는 사용할 수 있습니다 파괴 과제:
let [title, , pages] = book; // notice that we can just skip unnecessary values
console.log(title);
console.log(pages);
------------------
Amazing book
3
체크 아웃 할 수 있습니다 jsfiddle 위에서 제공 한 모든 코드와 함께.
ES6에는 이전에 일부 내부 방법을 노출시키는 잘 알려진 기호가 있으며,이를 사용하여 반복자 가이 개체의 작동 방식을 정의 할 수 있습니다.
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3",
*[Symbol.iterator]() {
yield *Object.keys(this);
}
};
[...p] //["p1", "p2", "p3"]
이것은 ES6 루프에서 사용하는 것과 동일한 결과를 제공합니다.
for(var key in p) {
console.log(key);
}
그러나 현재 ES6을 사용하는 기능을 아는 것이 중요합니다!
나는 확인하기보다는 이것을 할 것이다 obj.hasOwnerProperty
모든 내에서 for ... in
고리.
var obj = {a : 1};
for(var key in obj){
//obj.hasOwnProperty(key) is not needed.
console.log(key);
}
//then check if anybody has messed the native object. Put this code at the end of the page.
for(var key in Object){
throw new Error("Please don't extend the native object");
}
ES06부터 객체의 값을 배열로 가져올 수 있습니다.
let arrValues = Object.values( yourObject) ;
객체 값의 배열을 반환하고 프로토타입에서 값을 추출하지 않습니다!!
그리고 열쇠에 대해서는 (여기서 나보다 먼저 대답했습니다)
let arrKeys = Object.keys(yourObject);
반복하고 싶다면 생성 불가능한 특성 또한 사용할 수 있습니다 Object.getOwnPropertyNames(obj)
주어진 객체에 직접 찾은 모든 속성 (열거 가능 여부) 배열을 반환합니다.
var obj = Object.create({}, {
// non-enumerable property
getFoo: {
value: function() { return this.foo; },
enumerable: false
}
});
obj.foo = 1; // enumerable property
Object.getOwnPropertyNames(obj).forEach(function (name) {
document.write(name + ': ' + obj[name] + '<br/>');
});
최신 ES 스크립트에서는 다음과 같은 작업을 수행 할 수 있습니다.
Object.entries(p);
Object.entries()
기능:
var p = {
"p1": "value1",
"p2": "value2",
"p3": "value3"
};
for (var i in Object.entries(p)){
var key = Object.entries(p)[i][0];
var value = Object.entries(p)[i][1];
console.log('key['+i+']='+key+' '+'value['+i+']='+value);
}
Angular를 사용할 때 비슷한 문제가 있었는데 여기에 찾은 솔루션이 있습니다.
1 단계. 모든 객체 키를 가져옵니다. Object.keys 사용. 이 메소드는 주어진 개체 자체의 열거 가능한 속성의 배열을 반환합니다.
2 단계. 빈 배열을 만듭니다. 새로운 NGFOR 루프 가이 배열을 가리킬 것이기 때문에 모든 속성이 살아갈 곳입니다. 우리는 모두 잡아야합니다.3 단계. 반복 모든 키를 던지고 각 키를 생성 한 배열로 밀어 넣으십시오. 코드에서 어떻게 보이는지는 다음과 같습니다.
// Evil response in a variable. Here are all my vehicles.
let evilResponse = {
"car" :
{
"color" : "red",
"model" : "2013"
},
"motorcycle":
{
"color" : "red",
"model" : "2016"
},
"bicycle":
{
"color" : "red",
"model" : "2011"
}
}
// Step 1. Get all the object keys.
let evilResponseProps = Object.keys(evilResponse);
// Step 2. Create an empty array.
let goodResponse = [];
// Step 3. Iterate throw all keys.
for (prop of evilResponseProps) {
goodResponse.push(evilResponseProps[prop]);
}
다음은 원래 게시물에 대한 링크입니다. https://medium.com/@papaponmx/looping-over-object-properties-with-ngfor-in-angular-869cd7b2ddcc
.next () 메소드를 구현하면 객체가 반복자가됩니다.
const james = {
name: 'James',
height: `5'10"`,
weight: 185,
[Symbol.iterator]() {
let properties = []
for (let key of Object.keys(james)){
properties.push(key);
}
index = 0;
return {
next: () => {
let key = properties[index];
let value = this[key];
let done = index >= properties.length - 1 ;
index++;
return { key, value, done };
}
};
}
};
const iterator = james[Symbol.iterator]();
console.log(iterator.next().value); // 'James'
console.log(iterator.next().value); // `5'10`
console.log(iterator.next().value); // 185