Làm thế nào để lặp lại (khóa, giá trị) trong javascript?


335

Tôi có một từ điển có định dạng

dictionary = {0: {object}, 1:{object}, 2:{object}}

Làm thế nào tôi có thể lặp lại từ điển này bằng cách làm một cái gì đó như

for((key,value) in dictionary){
  //Do stuff where key would be 0 and value would be the object
}

3
for (let [key, value] of Object.entries(obj)), cần Babel.
elclanrs


1
@elclanrs Đó là vào ES2016 và nó chưa được chuẩn hóa :-)
thefourtheye


@dooagain, nó không phải là một mảng trong câu hỏi này.
zangw

Câu trả lời:


479

tl; dr

  1. Trong ECMAScript 5, điều đó là không thể.
  2. Trong ECMAScript 2015, có thể với Maps.
  3. Trong ECMAScript 2017, nó sẽ có sẵn.

Bản thảo 5:

Không, nó không thể với các đối tượng.

Bạn nên lặp lại với for..in, hoặc Object.keys, như thế này

for (var key in dictionary) {
    // check if the property/key is defined in the object itself, not in parent
    if (dictionary.hasOwnProperty(key)) {           
        console.log(key, dictionary[key]);
    }
}

Lưu ý: Điều ifkiện trên là cần thiết, chỉ khi bạn muốn lặp lại các thuộc tính là dictionarycủa riêng đối tượng. Bởi vì for..insẽ lặp qua tất cả các thuộc tính vô số được kế thừa.

Hoặc là

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

Bản thảo năm 2015

Trong ECMAScript 2015, bạn có thể sử dụng Mapcác đối tượng và lặp lại chúng với Map.prototype.entries. Trích dẫn ví dụ từ trang đó,

var myMap = new Map();
myMap.set("0", "foo");
myMap.set(1, "bar");
myMap.set({}, "baz");

var mapIter = myMap.entries();

console.log(mapIter.next().value); // ["0", "foo"]
console.log(mapIter.next().value); // [1, "bar"]
console.log(mapIter.next().value); // [Object, "baz"]

Hoặc lặp đi lặp lại với for..of, như thế này

'use strict';

var myMap = new Map();
myMap.set("0", "foo");
myMap.set(1, "bar");
myMap.set({}, "baz");

for (const entry of myMap.entries()) {
  console.log(entry);
}

Đầu ra

[ '0', 'foo' ]
[ 1, 'bar' ]
[ {}, 'baz' ]

Hoặc là

for (const [key, value] of myMap.entries()) {
  console.log(key, value);
}

Đầu ra

0 foo
1 bar
{} baz

Bản thảo năm 2017

ECMAScript 2017 sẽ giới thiệu một chức năng mới Object.entries. Bạn có thể sử dụng điều này để lặp lại đối tượng như bạn muốn.

'use strict';

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

Đầu ra

a 1
b 2
c 3

1
Một nghi ngờ cơ bản ở đây. Tôi đã đến đây để tìm cách làm điều này trong node.js, đó là javascript ở phía máy chủ. Làm thế nào để tôi biết phiên bản ES nào áp dụng trong trường hợp của tôi. Ngoài ra, trong trường hợp người dùng javascript thông thường, cách hỗ trợ phù hợp là gì vì tôi hiểu rằng phiên bản ES phụ thuộc vào trình duyệt của khách hàng?
Sandeepan Nath

2
@SandeepanNath Bạn có thể sử dụng các trang web như node.green để biết liệu một tính năng ES cụ thể có được hỗ trợ trong Node.js. Đối với các trình duyệt có liên quan, mọi người thường nhắm mục tiêu phiên bản được hỗ trợ rộng rãi, trong trường hợp này là ES5. Ngoài ra, các bộ chuyển đổi (như Babel ) giúp chuyển đổi mã ES2015 + sang ES5.
thefourtheye

1
Tôi thích Object.keys(dictionary).forEach(function(key) {…rất dễ đọc, và tương thích.
ctrl-alt-delor

5
Object.entries(object).forEach(([key, val]) => {...});
Krimson

Giải pháp ECMAScript 2015 ở trên đã ném "TypeScript và Iterator: Type 'IterableIterator <T>' không phải là một kiểu mảng" nhưng đơn giản ol myMap (). Foreach () hoạt động tốt.
ttugates

60

Thử cái này:

dict = {0:{1:'a'}, 1:{2:'b'}, 2:{3:'c'}}
for (var key in dict){
  console.log( key, dict[key] );
}

0 Object { 1="a"}
1 Object { 2="b"}
2 Object { 3="c"}

42

Các Object.entries()phương pháp đã được quy định tại ES2017 (và được hỗ trợ trong tất cả các trình duyệt hiện đại ):

for (const [ key, value ] of Object.entries(dictionary)) {
    // do something with `key` and `value`
}

Giải trình:

  • Object.entries()lấy một đối tượng như thế { a: 1, b: 2, c: 3 }và biến nó thành một mảng các cặp khóa-giá trị : [ [ 'a', 1 ], [ 'b', 2 ], [ 'c', 3 ] ].

  • Với for ... ofchúng ta có thể lặp qua các mục của mảng đã tạo.

  • Vì chúng tôi được đảm bảo rằng mỗi mục mảng lặp đi lặp lại chính nó là một mảng hai mục nhập, chúng tôi có thể sử dụng hàm hủy để gán trực tiếp các biến keyvaluecho mục thứ nhất và thứ hai của nó.


Điều đáng buồn là mọi người vẫn sử dụng Internet Explorer
Edward

Tôi đau đớn nhận ra. Babel và polyfill.io giải quyết điều này, nhưng nó không thú vị lắm.
Loilo

19

Bạn có thể làm một cái gì đó như thế này:

dictionary = {'ab': {object}, 'cd':{object}, 'ef':{object}}
var keys = Object.keys(dictionary);

for(var i = 0; i < keys.length;i++){
   //keys[i] for key
   //dictionary[keys[i]] for the value
}

3
Xinh đẹp! Tôi thích cách câu trả lời của bạn hoạt động trong ECMAscript 5 mặc dù câu trả lời được chấp nhận và được đánh giá cao nhất nói rằng điều đó là không thể. Bạn xứng đáng với tất cả các upvote nhiều hơn.
liljoshu

18

Thử cái này:

var value;
for (var key in dictionary) {
    value = dictionary[key];
    // your code here...
}

9

CHÀO MỪNG ĐẾN NĂM 2020 * Giọt nước trong ES6 *

Có một số câu trả lời khá cũ ở đây - tận dụng lợi thế của việc phá hủy. Theo tôi đây không phải nghi ngờ gì là cách tốt nhất (rất dễ đọc) để lặp lại một đối tượng.

Object.entries(myObject).forEach(([k,v]) => {
    console.log("The key: ",k)
    console.log("The value: ",v)
})

Chỉ cần một lưu ý: nếu bạn thay thế forEachbằng mapở trên, thì có thể tổng hợp các giá trị. mapsau đó sẽ trả về một danh sách các giá trị đã nói, do đó có khả năng đơn giản hóa mã theo các cách khác.
Lazerbeak12345


1

sử dụng swagger-ui.js

bạn có thể làm được việc này -

_.forEach({ 'a': 1, 'b': 2 }, function(n, key) {
    console.log(n, key);
 });

0

Bạn có thể sử dụng kịch bản dưới đây.

var obj={1:"a",2:"b",c:"3"};
for (var x=Object.keys(obj),i=0;i<x.length,key=x[i],value=obj[key];i++){
    console.log(key,value);
}

đầu ra
1 a
2 b
c 3


#will đầu ra #c 3 # 1 a # 2 b
Michael Piper

4
Xem xét thêm một lời giải thích cho câu trả lời của bạn, mã một mình là ít hữu ích. Ngoài ra, bạn có thể chỉnh sửa câu trả lời của mình, các bình luận không có nghĩa là một phần mở rộng cho câu trả lời theo cách bạn đang sử dụng chúng
Viktor

0

Để cải thiện câu trả lời được chấp nhận, để giảm lồng nhau, bạn có thể thực hiện việc này thay vào đó, với điều kiện là khóa không được kế thừa:

for (var key in dictionary) {
    if (!dictionary.hasOwnProperty(key)) {
        continue;
    }
    console.log(key, dictionary[key]);
}

Chỉnh sửa: thông tin về Object.hasOwnProperty đây

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.