Usando objects em for loops

Por que não é possível usar objects for loops? Ou isso é um bug do navegador? Este código não funciona no Chrome 42, dizendo que o indefinido não é uma function:

test = { first: "one"} for(var item of test) { console.log(item) } 

O loop for..of suporta apenas objects iteráveis, como matrizes, não objects.

Para iterar sobre os valores de um object, use:

 for (var key in test) { var item = test[key]; } 

Se você estiver armazenando dados em um armazenamento de valor-chave, use o Map que é projetado explicitamente para essa finalidade.

Se você tiver que usar um object, o ES2017 (ES8) permite que você use Object.values :

 const foo = { a: 'foo', z: 'bar', m: 'baz' }; for (let value of Object.values(foo)) { console.log(value); } 

Se isso ainda não for suportado, use um polyfill: Versão alternativa para Object.values()

E, finalmente, se você estiver suportando um ambiente antigo que não suporta esta syntax, você terá que recorrer ao uso das forEach e Object.keys :

 var obj = { a: 'foo', z: 'bar', m: 'baz' }; Object.keys(obj).forEach(function (prop) { var value = obj[prop]; console.log(value); }); 

Você pode usar esta syntax:

 let myObject = {first: "one"}; for(let [key, value] of Object.entries(myObject)) { console.log(key, value); // "first", "one" } 

No entanto, Object.entries tem pouco apoio agora não funciona no IE ou no iOS Safari. Você provavelmente precisará de um polyfill.

Eu fiz objects iteráveis ​​com este código:

 Object.prototype[Symbol.iterator] = function*() { for(let key of Object.keys(this)) { yield([ key, this[key] ]) } } 

Uso:

 for(let [ key, value ] of {}) { } 

Iterator, Iterable e for..of loop no ECMAScript 2015 / ES6

 let tempArray = [1,2,3,4,5]; for(element of tempArray) { console.log(element); } // 1 // 2 // 3 // 4 // 5 

Mas se fizermos

 let tempObj = {a:1, b:2, c:3}; for(element of tempObj) { console.log(element); } // error 

Recebemos erro porque o loop for..of funciona apenas em Iterables , ou seja, o object que possui um iterador @@ que adere ao protocolo Iterator , o que significa que ele deve ter um object com um próximo método. O próximo método não recebe argumentos e deve retornar um object com essas duas propriedades.

done : sinaliza que a sequência terminou quando true e false significa que pode haver mais valores: este é o item atual na sequência

Então, para fazer um object itterable que é para fazer funcionar com for ..of nós podemos:

1.Faça um object um Iterable atribuindo a sua propriedade mística @@ iterator através da propriedade Symbol.iterator.Aqui está como:

 let tempObj = {a:1, b:2, c:3}; tempObj[Symbol.iterator]= () => ({ next: function next () { return { done: Object.keys(this).length === 0, value: Object.keys(this).shift() } } }) for(key in tempObj){ console.log(key) } // a // b // c 

2. Use Object.entries , que retorna um Iterable :

 let tempObj = {a:1, b:2, c:3}; for(let [key, value] of Object.entries(tempObj)) { console.log(key, value); } // a 1 // b 2 // c 3 

3. Use Object.keys , aqui está como:

 let tempObj = {a:1, b:2, c:3}; for (let key of Object.keys(tempObj)) { console.log(key); } // a // b // c 

Espero que isto ajude!!!!!!

Porque o literal de object não possui a propriedade Symbol.iterator . Para ser específico, você só pode iterar sobre String , Array , Map , Set , argumentos , NodeList (não suporta amplamente) e Generator com for … of loop.

Para lidar com a iteração Literal do Objeto, você tem duas opções.

para … em

 for(let key in obj){ console.log(obj[key]); } 

Object.keys + forEach

 Object.keys(obj).forEach(function(key){ console.log(obj[key]); }); 

A resposta é Não. Não é possível usar For..Of com literais de object.

Concordo com Overv que For..Of é apenas para iterações. Eu tive exatamente a mesma pergunta porque eu uso objects para iterar sobre chaves e valores com for..in. Mas acabei de perceber que é para isso que os ES6 MAPS e o SETS são.

 let test = new Map(); test.set('first', "one"); test.set('second', "two"); for(var item of test) { console.log(item); // "one" "two" } 

Por isso, ele atinge o objective de não ter que usar for..In (validando com hasOwnProperty ) e não ter que usar Object.keys ().

Além disso, suas chaves não estão limitadas a seqüências de caracteres. Você pode usar números, objects ou outros literais.

Os literais de object não possuem iteradores internos, que são necessários para trabalhar com for...of loops. No entanto, se você não quiser passar pelo problema de adicionar seu próprio [Symbol.iterator] ao seu object, basta usar o método Object.keys() . Esse método retorna um object Array , que já possui um iterador integrado, para que você possa usá-lo com um loop for...of como este:

 const myObject = { country: "Canada", province: "Quebec", city: "Montreal" } for (let i of Object.keys(myObject)) { console.log("Key:", i, "| Value:", myObject[i]); } //Key: country | Value: Canada //Key: province | Value: Quebec //Key: city | Value: Montreal 

É possível definir um iterador sobre qualquer object de doação, dessa forma você pode colocar lógica diferente para cada object

 var x = { a: 1, b: 2, c: 3 } x[Symbol.iterator] = function* (){ yield 1; yield 'foo'; yield 'last' } 

Então apenas diretamente iterar x

 for (let i in x){ console.log(i); } //1 //foo //last 

É possível fazer a mesma coisa no object Object.prototype E ter um iterador geral para todos os objects

 Object.prototype[Symbol.iterator] = function*() { for(let key of Object.keys(this)) { yield key } } 

então iterar seu object assim

 var t = {a :'foo', b : 'bar'} for(let i of t){ console.log(t[i]); } 

Ou assim

 var it = t[Symbol.iterator](), p; while(p = it.next().value){ console.log(t[p]) } 

Eu fiz o seguinte para consolar facilmente as minhas coisas.

 for (let key in obj) { if(obj.hasOwnProperty(key){ console.log(`${key}: ${obj[key]}`); } } 

Que tal usar

 function* entries(obj) { for (let key of Object.keys(obj)) { yield [key, obj[key]]; } } for ([key, value] of entries({a: "1", b: "2"})) { console.log(key + " " + value); } 

no ES6 você poderia ir com o gerador:

 var obj = {1: 'a', 2: 'b'}; function* entries(obj) { for (let key of Object.keys(obj)) { yield [key, obj[key]]; } } let generator = entries(obj); let step1 = generator.next(); let step2 = generator.next(); let step3 = generator.next(); console.log(JSON.stringify(step1)); // {"value":["1","a"],"done":false} console.log(JSON.stringify(step2)); // {"value":["2","b"],"done":false} console.log(JSON.stringify(step3)); // {"done":true} 

Aqui está o jsfiddle. Na saída, você obterá um object com as chaves "value" e "done" . "Value" contém tudo o que você quer que ele tenha e "done" é o estado atual da iteração no bool.

Que tal usar Object.keys para obter uma matriz de chaves? E então, para sempre, no Array ?

obj = { a: 1, b:2} Object.keys(obj).forEach( key => console.log(`${key} => ${obj[key]}`))