Heim > Artikel > Web-Frontend > Eine kurze Diskussion über mehrere gängige Methoden zum Durchlaufen von Arrays und Objekten in JavaScript
Arrays und Objekte spielen in verschiedenen Programmiersprachen eine wichtige Rolle. In diesem Artikel werden die häufig verwendeten Array-Traversal- und Objekt-Traversal-Methoden in JavaScript, die Unterschiede zwischen den einzelnen Methoden und Vorsichtsmaßnahmen bei deren Verwendung vorgestellt.
Mit der kontinuierlichen Weiterentwicklung von JS gibt es ab der ES7-Spezifikation mehr als zehn Traversal-Methoden. Im Folgenden finden Sie eine Gruppe von Methoden mit ähnlichen Funktionen, um die gängigen Durchlaufmethoden für Arrays vorzustellen.
for, forEach, for...of
const list = [1, 2, 3, 4, 5, 6, 7, 8,, 10, 11]; for (let i = 0, len = list.length; i < len; i++) { if (list[i] === 5) { break; // 1 2 3 4 // continue; // 1 2 3 4 6 7 8 undefined 10 11 } console.log(list[i]); } for (const item of list) { if (item === 5) { break; // 1 2 3 4 // continue; // 1 2 3 4 6 7 8 undefined 10 11 } console.log(item); } list.forEach((item, index, arr) => { if (item === 5) return; console.log(index); // 0 1 2 3 5 6 7 9 10 console.log(item); // 1 2 3 4 6 7 8 10 11 });
Zusammenfassung
some, every
const list = [ { name: '头部导航', backward: false }, { name: '轮播', backward: true }, { name: '页脚', backward: false }, ]; const someBackward = list.some(item => item.backward); // someBackward: true const everyNewest = list.every(item => !item.backward); // everyNewest: false
Zusammenfassung
const list = [
{ name: '头部导航', type: 'nav', id: 1 },,
{ name: '轮播', type: 'content', id: 2 },
{ name: '页脚', type: 'nav', id: 3 },
];
const resultList = list.filter(item => {
console.log(item);
return item.type === 'nav';
});
// resultList: [
// { name: '头部导航', type: 'nav', id: 1 },
// { name: '页脚', type: 'nav', id: 3 },
// ]
const newList = list.map(item => {
console.log(item);
return item.id;
});
// newList: [1, empty, 2, 3]
// list: [
// { name: '头部导航', type: 'nav', id: 1 },
// empty,
// { name: '轮播', type: 'content', id: 2 },
// { name: '页脚', type: 'nav', id: 3 },
// ]
Zusammenfassung
Beide generieren ein neues Array und ändern das ursprüngliche Array nicht (mit Ausnahme des Durchlaufens des Objektarrays und der Bedienung des Elementobjekts in der Rückruffunktion)
Beide überspringen leere Elemente. Interessierte Schüler können es selbst ausdrucken.const list = [
{ name: '头部导航', id: 1 },
{ name: '轮播', id: 2 },
{ name: '页脚', id: 3 },
];
const result = list.find((item) => item.id === 3);
// result: { name: '页脚', id: 3 }
result.name = '底部导航';
// list: [
// { name: '头部导航', id: 1 },
// { name: '轮播', id: 2 },
// { name: '底部导航', id: 3 },
// ]
const index = list.findIndex((item) => item.id === 3);
// index: 2
list[index].name // '底部导航';
Summary
Beide werden zum Suchen von Array-Elementen verwendet.
Die Suchmethode gibt den Wert des ersten Elements im Array zurück, das die Rückruffunktion erfüllt. Gibt undefiniert zurück, wenn es nicht existiert.reduce empfängt zwei Parameter, der erste Parameter ist die Rückruffunktion (Callback) und der zweite Parameter ist der Anfangswert (initialValue). Die Methode „reduceRight“ stimmt vollständig mit ihr überein, mit der Ausnahme, dass sie in die entgegengesetzte Richtung der Ausführung von „reduce“ erfolgt (von rechts nach links).
Die Rückruffunktion erhält vier Parameter:
Akkumulator: MDN erklärt es als Akkumulator, aber ich halte es für unangemessen, es sollte das akkumulierte Ergebnis aller vorherigen Array-Elemente sein, die von der Rückruffunktion verarbeitet wurden des aktuellen Elements. aktuell: Das Array-Element, das gerade ausgeführt wird.const list = [ { name: 'left', width: 20 }, { name: 'center', width: 70 }, { name: 'right', width: 10 }, ]; const total = list.reduce((currentTotal, item) => { return currentTotal + item.width; }, 0); // total: 100
Deduplizierung des Objektarrays und zählen Sie die Anzahl der Wiederholungen jedes Elements
const list = [ { name: 'left', width: 20 }, { name: 'right', width: 10 }, { name: 'center', width: 70 }, { name: 'right', width: 10 }, { name: 'left', width: 20 }, { name: 'right', width: 10 }, ]; const repeatTime = {}; const result = list.reduce((array, item) => { if (repeatTime[item.name]) { repeatTime[item.name]++; return array; } repeatTime[item.name] = 1; return [...array, item]; }, []); // repeatTime: { left: 2, right: 3, center: 1 } // result: [ // { name: 'left', width: 20 }, // { name: 'right', width: 10 }, // { name: 'center', width: 70 }, // ]
Ermitteln Sie den Maximal-/Minimalwert des Objektarrays
const list = [ { name: 'left', width: 20 }, { name: 'right', width: 30 }, { name: 'center', width: 70 }, { name: 'top', width: 40 }, { name: 'bottom', width: 20 }, ]; const max = list.reduce((curItem, item) => { return curItem.width >= item.width ? curItem : item; }); const min = list.reduce((curItem, item) => { return curItem.width <= item.width ? curItem : item; }); // max: { name: "center", width: 70 } // min: { name: "left", width: 20 }
reduce ist sehr leistungsstark und noch mehr. Duoqi Jiyinqiao empfiehlt, sich diesen Artikel „25 erweiterte Array-Reduzierung, die Sie kennen müssen“ anzusehen Traversierungsmethoden? Versuchen wir es im Chrome-Browser. Ich führe jede Schleife zehnmal aus, entferne die Maximal- und Minimalwerte und errechne den Durchschnitt, um den Fehler zu reduzieren. var list = Array(100000).fill(1)
console.time('for');
for (let index = 0, len = list.length; index < len; index++) {
}
console.timeEnd('for');
// for: 2.427642822265625 ms
console.time('every');
list.every(() => { return true })
console.timeEnd('every')
// some: 2.751708984375 ms
console.time('some');
list.some(() => { return false })
console.timeEnd('some')
// some: 2.786590576171875 ms
console.time('foreach');
list.forEach(() => {})
console.timeEnd('foreach');
// foreach: 3.126708984375 ms
console.time('map');
list.map(() => {})
console.timeEnd('map');
// map: 3.743743896484375 ms
console.time('forof');
for (let index of list) {
}
console.timeEnd('forof')
// forof: 6.33380126953125 ms
Aus den Druckergebnissen geht hervor, dass die for-Schleife am schnellsten und die for-of-Schleife am langsamsten ist
是否可终止 | ||||
---|---|---|---|---|
** | break | continue | return | 性能(ms) |
for | 终止 ✅ | 跳出本次循环 ✅ | ❌ | 2.42 |
forEach | ❌ | ❌ | ❌ | 3.12 |
map | ❌ | ❌ | ❌ | 3.74 |
for of | 终止 ✅ | 跳出本次循环 ✅ | ❌ | 6.33 |
some | ❌ | ❌ | return true ✅ | 2.78 |
every | ❌ | ❌ | return false ✅ | 2.75 |
最后,不同浏览器内核 也会有些差异,有兴趣的同学也可以尝试一下。
在对象遍历中,经常需要遍历对象的键、值,ES5 提供了 for...in 用来遍历对象,然而其涉及对象属性的“可枚举属性”、原型链属性等,下面将从 Object 对象本质探寻各种遍历对象的方法,并区分常用方法的一些特点。
for in
Object.prototype.fun = () => {};const obj = { 2: 'a', 1: 'b' };for (const i in obj) { console.log(i, ':', obj[i]);}// 1: b// 2: a// fun : () => {} Object 原型链上扩展的方法也被遍历出来for (const i in obj) { if (Object.prototype.hasOwnProperty.call(obj, i)) { console.log(i, ':', obj[i]); }}// name : a 不属于自身的属性将被 hasOwnProperty 过滤
小结
使用 for in 循环时,返回的是所有能够通过对象访问的、可枚举的属性,既包括存在于实例中的属性,也包括存在于原型中的实例。如果只需要获取对象的实例属性,可以使用 hasOwnProperty 进行过滤。
使用时,要使用(const x in a)
而不是(x in a)
后者将会创建一个全局变量。
for in 的循环顺序,参考【JavaScript 权威指南】(第七版)6.6.1。
Object.keys
Object.prototype.fun = () => {};const str = 'ab';console.log(Object.keys(str));// ['0', '1']const arr = ['a', 'b'];console.log(Object.keys(arr));// ['0', '1']const obj = { 1: 'b', 0: 'a' };console.log(Object.keys(obj));// ['0', '1']
小结
用于获取对象自身所有的可枚举的属性值,但不包括原型中的属性,然后返回一个由属性名组成的数组。
Object.values
Object.prototype.fun = () => {};const str = 'ab';console.log(Object.values(str));// ['a', 'b']const arr = ['a', 'b'];console.log(Object.values(arr));// ['a', 'b']const obj = { 1: 'b', 0: 'a' };console.log(Object.values(obj));// ['a', 'b']
小结
用于获取对象自身所有的可枚举的属性值,但不包括原型中的属性,然后返回一个由属性值组成的数组。
Object.entries
const str = 'ab';for (const [key, value] of Object.entries(str)) { console.log(`${key}: ${value}`);}// 0: a// 1: bconst arr = ['a', 'b'];for (const [key, value] of Object.entries(arr)) { console.log(`${key}: ${value}`);}// 0: a// 1: bconst obj = { 1: 'b', 0: 'a' };for (const [key, value] of Object.entries(obj)) { console.log(`${key}: ${value}`);}// 0: a// 1: b
小结
用于获取对象自身所有的可枚举的属性值,但不包括原型中的属性,然后返回二维数组。每一个子数组由对象的属性名、属性值组成。可以同时拿到属性名与属性值的方法。
Object.getOwnPropertyNames
Object.prototype.fun = () => {};Array.prototype.fun = () => {};const str = 'ab';console.log(Object.getOwnPropertyNames(str));// ['0', '1', 'length']const arr = ['a', 'b'];console.log(Object.getOwnPropertyNames(arr));// ['0', '1', 'length']const obj = { 1: 'b', 0: 'a' };console.log(Object.getOwnPropertyNames(obj));// ['0', '1']
小结
用于获取对象自身所有的可枚举的属性值,但不包括原型中的属性,然后返回一个由属性名组成的数组。
我们对比了多种常用遍历的方法的差异,在了解了这些之后,我们在使用的时候需要好好思考一下,就能知道那个方法是最合适的。欢迎大家纠正补充。
更多编程相关知识,请访问:编程视频!!
Das obige ist der detaillierte Inhalt vonEine kurze Diskussion über mehrere gängige Methoden zum Durchlaufen von Arrays und Objekten in JavaScript. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!