嗨大家好,昨天的練習應該不難。請看下面的解答:
//第一題:請問下面 console.log 會出現哪個顏色?
let color = ["red","green","blue"];
console.log(color[2]); //答案是藍色
//第二題:承上,我要怎麼取出紅色?
color[0] //可用 console.log(color[0]); 檢查
//第三題:我想要新增橘色,變成陣列的第四筆資料,要怎麼寫?
color.push("orange"); //可用 console.log(color); 檢查
//第四題:我發現我打錯了,第四筆資料應該是黃色才對,請問我要怎樣把第四筆資料改成黃色?
color[3] = "yellow"; //可用 console.log(color); 檢查
//第五題:我懶得數 color 裡有幾筆資料,我要怎麼打,讓電腦自動告訴我答案?
color.length; //可用 console.log(color.length); 檢查
今天我們要補充一些昨天還沒講到的知識(你也可以把它當成咒語),那現在就跟我一起出發吧!
有時候我想要讓陣列的前面新增一筆或多筆資料,這個時候就可以使用 陣列名 + .unshift(要加到陣列的東西1,要加到陣列的東西2,...) 。寫法如下:
let ary = [1,2,3];
ary.unshift("數字要開始囉",0);
console.log(ary); //印出["數字要開始囉",0,1,2,3]
當我想要讓陣列裡的第一筆資料變成最後一筆資料,最後一筆資料變成第一筆資料時,不需要人工作業,可以直接使用 陣列名 + .reverse 解決。寫法如下:
let ary = [1,2,3];
ary.reverse();
console.log(ary); //印出[3, 2, 1]
到這裡為止應該都很簡單吧!相信你一定用過 excel ,下面幾個咒語跟 excel 的功能有些類似。我們還剩三個咒語,加油!
當陣列裡的數字亂七八糟,想讓數字們從小排到大,或從大排到小嗎? 你需要這樣寫:
你可以自行命名參數的名字。我知道這樣很難記住,所以來實際寫寫看吧!
let arr = [2,3,4,1,5,6,7];
//從大排到小
arr.sort(function(x,y){
return y-x;
});
console.log(arr); //印出[7, 6, 5, 4, 3, 2, 1]
//從小排到大
arr.sort(function(x,y){
return x-y;
});
console.log(arr); //印出[1, 2, 3, 4, 5, 6, 7]
-----2021/02/09 補充-----
sort 的特性是從每個值的最左邊開始比較,能重新將陣列與物件排序。什麼意思呢?舉例來說如果一個陣列是這樣:array = [1,2,10,15,3]
,那單純只打 array.sort();
會得到 [1, 10, 15, 2, 3]
。因為 [1,2,10,15,3] 這五個值的最左邊分別是 1、2、1、1、3 ,導致 10 跟 15 反而排到 2 和 3 前面。為此如果要讓陣列裡的數字,以數字大小來排列時,才需要如上所說的動點小手腳(?):
//從小排到大
array.sort(function(a, b) {
return a - b;
});
//從大排到小
array.sort(function(a, b) {
return b - a;
});
當你想從陣列中挑出某些符合條件的資料,就可以使用 filter(function(參數)){ return + 條件} 。實際範例如下:
let arr = [2,3,4,5,6,7];
let arrLower5 = arr.filter(function(e){
return e<5; //回傳小於5的參數
});
console.log(arrLower5); //印出[2, 3, 4]
會宣告 arrLower5 這個變數,是因為要讓它印出,如果單純把 console.log 寫在 return 下面,不會被執行。但是把 console.log(e) 放到函式外面,會得到 e is not defined 。因此給它一個名字,再用 console.log 把它印出來。
最後我們來看 indexOf() 。這句話會回傳在陣列裡符合條件,並且第一筆被找到的資料在陣列裡的哪個位置。如果陣列裡都找不到,則會回傳 -1 。寫法為: 陣列名 + .indexOf(要查找的資料)
let arr = ["A","B","C","D"];
console.log(arr.indexOf("A")); //印出0
舉例來說,在上面的例子中,當我想要找 A 這筆資料,可以把它放進 indexOf 後面的括號,因為它是字串,所以還要額外加上雙引號。 console.log 則會印出它在第 0 個位置,注意!陣列的第 0 個位置,其實是第一筆資料。
同時,我也可以設定說我要從第幾筆開始查找,只要在本來的例句後面加上逗號,標註第幾位即可:陣列名 + .indexOf(要查找的資料,第幾個位置開始查)
let arr = ["A","B","C","D","B","C","B"];
console.log(arr.indexOf("B",3)); //印出4
console.log(arr.indexOf("B",4)); //還是印出4
console.log(arr.indexOf("B",5)); //印出6
console.log(arr.indexOf("D",5)); //印出-1
上面的範例中,共有四個 console.log 。第一題要從第 3 個位置開始找 B ,也就是從 ["D","B","C","B"]
中去尋找,找到的第一個 B 位在["A","B","C","D","B","C","B"]
的第 4 個位置(第五筆資料),因此印出 4 。第二題從第 4 個位置開始找,,也就是從 ["B","C","B"]
中尋找,因此還是印出 4 。第三題應該不用再解釋,會印出 6 。至於第四題,因為第 5 個位置開始,找不到 D 了,所以印出 -1 。
-----2021/02/09 補充-----
使用 indexOf 尋找陣列中包了陣列的值時,發現就算明明有那個值,卻找不到東西。這才發現我對於 indexOf 的了解還不夠扎實,在此也補充一下觀念。
舉例來說,當我有一堆資料 arr = [[3,0],[1,2],[5,0],[10,3]],想從裡面找到 [3,0] 在 arr 的第幾個位置,直接使用 arr.indexOf("[3,0]") 會找不到並得到 -1 ,但裡面明明有這個值啊!
其實這是因為 indexOf 是用嚴格模式 (===) 判斷,而陣列是物件的一種,比較物件時,只有當這兩個物件的內容物完全相同才會得到 true ,不然即使其中有幾個值相同也會得到 false 。
那麼要怎麼解決呢?可以自己用 for 迴圈寫一個客製化 indexOf 函式。
function indexOfCustom (parentArray, searchElement) {
for (let i = 0; i < parentArray.length; i++ ) {
if ( parentArray[i][0] == searchElement[0] && parentArray[i][1] == searchElement[1] && parentArray[i][2] == searchElement[2] && parentArray[i][3] == searchElement[3]) {
return i;
}
}
return -1;
}
因為陣列是從0開始數,預設代表陣列位置的變數i=0。當i小於查找項目的長度,跑下面的迴圈,跑完加一再繼續跑,直到等於長度時停止。從查找陣列的第0項開始,當第0項陣列中的第0個位置的值,跟要找的陣列的第0個值相同,就讓i顯示0返回,藉此得知要找的就在第0的位置,依此類推,若都找不到則返回-1。parentArray[i][0] == searchElement[0]
這裡要寫多少個,則端看你的 searchElement 陣列中有幾個值。
其實陣列還有很多很多能玩的,沒有辦法一一介紹,有興趣或是在實際應用中遇到的時候,可以再呼叫 Google 神燈精靈出來幫忙唷!
-----2021/02/24 補充-----
若要複製陣列,再進行 sort 等動作,以免動到原始陣列,可以使用[...陣列名]
。例如:
let arr = [1,3,2];
let arrCopy = [...arr];
console.log(arrCopy); //確認複製有成功
arrCopy = arrCopy.sort();
console.log(arrCopy); //複製的印出 [1,2,3]
console.log(arr); //原本的仍印出 [1,3,2]
如果直接指定 let arrCopy = arr
,在做 sort() 時會發現原本的也被動到了:
let arr = [1,3,2];
let arrCopy = arr;
console.log(arrCopy); //確認複製有成功
arrCopy = arrCopy.sort();
console.log(arrCopy); //複製的印出 [1,2,3]
console.log(arr); //原本的也跟著印出 [1,2,3],失去複製的意義
JS 學徒特訓班教學影片及練習題 22-23 + 27 關
JavaScript 陣列處理方法 [filter(), find(), forEach(), map(), every(), some(), reduce()]:https://wcc723.github.io/javascript/2017/06/29/es6-native-array/#Array-prototype-filter
Array.prototype.indexOf(): https://developer.mozilla.org/zh-TW/docs/Web/JavaScript/Reference/Global_Objects/Array/indexOf
Javascript indexOf for an array of arrays not finding array: https://stackoverflow.com/questions/10260165/javascript-indexof-for-an-array-of-arrays-not-finding-array