在 JavaScript 中計算陣列的某些元素出現的次數
-
在 JavaScript 中使用
.filter
方法來計數陣列中的某些元素 -
在 JavaScript 中使用
.reduce
方法執行回撥函式 -
在 JavaScript 中使用
.prototype
陣列實體編寫自定義方法或屬性
介紹一下 .filter
方法,該方法可用於根據條件過濾陣列元素,除了 .length
屬性外,我們還可以使用它來計算陣列的某些元素。函式提供 .filter
方法的條件,作為引數傳遞。
此外,我們將介紹 .reduce
方法,該方法為陣列中的每個元素執行一個函式並返回一個值。
作為引數傳遞的函式可以是箭頭函式,也可以是作為回撥函式的普通函式。它將指示 .filter
將新增到返回陣列中的元素或 .reduce
方法將對陣列中的每個元素執行什麼操作。
在 JavaScript 中使用 .filter
方法來計數陣列中的某些元素
.filter
是 Array
實體的一個方法,它返回一個由提供的條件過濾的新陣列。返回一個新陣列意味著呼叫該方法的原始陣列將保持不變。
例如,如果我們想要陣列中所有等於值 one
的元素,我們可以使用 .filter
,如下所示:
// Input
let array = ['one', 'two', 'three', 'four', 'five']
array = array.filter(element => element == 'one')
console.log(array)
輸出:
// Output
[ 'one' ]
正如預期的那樣,.filter
方法返回了一個基於 element == 'one'
條件的陣列。因此,如果陣列的實際元素等於'one'
,則過濾器會將這個元素新增到返回的陣列中。
但是 .filter
方法內部發生了什麼?通過對 condition()
函式使用通用函式結構,我們可以看得更清楚:
// Input
let array = ['one', 'two', 'three', 'four', 'five']
array = array.filter(function condition(element) {
if (element == 'one') return true
return false
})
console.log(array)
有了這個,我們有相同的第一個示例輸出:
// Output
[ 'one' ]
condition()
函式接收一個 element
作為引數,如果此 element
等於某個值,在本例中為 'one'
,則返回 true
,否則返回錯誤的
。
因此,.filter
方法新增條件導致 true
的任何元素
;由於原始陣列只有第一個元素為 one
,因此 .filter
僅返回一個元素。
請注意,condition()
函式是在 .filter
方法中宣告的。如果你在外面宣告它並在 filter
中呼叫它,它不會起作用,因為 element
是回撥範圍的一部分。
回撥函式作為引數傳遞給另一個稱為外部函式
的函式。
外層函式會呼叫回撥函式做某事;在 .filter
方法的情況下,它將呼叫 condition()
回撥函式以根據其條件過濾陣列。
回到我們的目標,.filter
最終將返回一個帶有 array.length
元素的新陣列,每個元素都是一個元素,其回撥函式返回的值等於 true
。我們可以很容易地使用 .length
屬性來計算這些過濾後的元素。
.length
是陣列實體的一個屬性,它返回陣列中元素的數量。這個數字總是大於該陣列中的最高索引,因為第一個元素總是在索引上等於 0
。
// Input
let array = [1, 2, 3, 4, 5]
console.log(array.length)
輸出:
// Output
5
array
中的元素數為 5。5 大於值 5
的索引,即 4。
綜上所述,作為一個例子,我們可以使用以下內容:如何獲得大於七的學校的所有測試筆記的數量?測試筆記的陣列在示例中。
// Input
let notes = [7.0, 6.7, 7.3, 9.8, 5.6, 7.1, 7.8, 6.2, 8.0, 9.0, 4.5, 6.9, 7.5, 8.5, 6.4]
greaterThanSeven = notes.filter(value => value > 7)
console.log(greaterThanSeven.length)
輸出:
// Output (The array returned by the .filter is: [7.3, 9.8, 7.1, 7.8, 8, 9, 7.5, 8.5])
8
因此,8
是原始 notes
陣列中所有 15 個音符中大於 7 的音符數。
在 JavaScript 中使用 .reduce
方法執行回撥函式
我們可以使用 .reduce
陣列實體方法作為另一種選擇。此方法用於對每個陣列元素執行回撥函式(和 .filter
),但最終會返回一個值。
.reduce
工作的一個簡單示例是陣列中所有元素的總和:
// Input
let array = [1, 2, 3, 4, 5].reduce((previous, current) => previous + current)
console.log(array)
輸出:
// Output
15
但是我們可以通過傳遞初始值以另一種方式使用此方法。在前面的例子中,我們可以看到 previous
從陣列中的第一個索引元素開始,作為回撥函式,這樣:
/*
previous + current = result
1 + 2 = 3
3 + 3 = 6
6 + 4 = 10
10 + 5 = 15 -> final result
*/
這個總和有效,因為如果我們不將第二個引數(因為回撥函式是第一個引數)傳遞給 .reduce
方法,它將在第一次迭代中將 previous
視為陣列的第一個元素。
但是如果我們想計算陣列中的某些元素呢?我們不能將第一個元素用作 previous
,因為它可能導致錯誤的值。
下面的示例是關於計算陣列中有多少 2 個數字:
// Input
let array = [1, 2, 3, 4, 5].reduce((sum, value) => (value == 2 ? sum + 1 : sum))
console.log(array)
輸出:
// Output
2
如我們所見,結果是 2
,但正確答案是 1
。發生這種情況是因為 sum
是用第一個元素 1
初始化的,因為我們沒有傳遞迴調函式之外的任何其他引數。
為了進行更正,我們可以傳遞一個 0
作為第二個 .reduce
引數:
// Input
let array = [1, 2, 3, 4, 5].reduce((sum, value) => (value == 2 ? sum + 1 : sum), 0)
console.log(array)
輸出:
// Output
1
這樣,每次當前元素等於 2 時,.reduce
都會產生 sum + 1
,而 sum
初始化為 0
。
在 JavaScript 中使用 .prototype
陣列實體編寫自定義方法或屬性
作為一個優點,我們可以使用 .prototype
陣列實體屬性來向該實體寫入自定義方法或屬性,而不是每次需要計算陣列中的某些元素時都使用所有這些邏輯。
要為陣列實體建立一個 .countCertainElements
方法,我們可以使用以下結構:
// Input
// Declaring the prototype .countCertainElements method
Array.prototype.countCertainElements = function(value){
return this.filter(arrayElement => arrayElement == value).length
}
let array1 = [1, 2, 2, 2, 3, 4, 5]
console.log(array1.countCertainElements(2))
輸出:
// Output
3
我們可以對 .reduce
做同樣的事情:
// Input
// Declaring the prototype .countCertainElements method
Array.prototype.countCertainElements = function(value){
return this.reduce((sum, element) => (element == value ? sum + 1 : sum), 0)
}
let array1 = [1, 2, 2, 2, 3, 4, 5]
console.log(array1.countCertainElements(2))
輸出:
// Output
3