【js基礎】js數組方法總結

補充:git

JavaScript 語言和宿主環境中許多新的內置函數,都提供了一個可選的參數,一般被稱爲「上下文」(context),其做用和 bind(..) 同樣,確保你的回調函數使用指定的 this。
function foo(el) {
 console.log( el, this.id );
}
var obj = {
 id: "awesome"
};
// 調用 foo(..) 時把 this 綁定到 obj
[1, 2, 3].forEach( foo, obj );
// 1 awesome 2 awesome 3 awesome

es5部分

一、map [es5]

不改變原數組
須要一個函數做爲參數, 依次處理數組內每一個元素,並返回新的值,無返回值則爲undefined
使用全部的返回值組成新的數組es6

console.log(['a','b','c'].map((elem, index) => {
    console.log(elem, index)
    /*a 0
    *b 1
    *c 2
    */
    if (elem === 'a') return 'this is a'
}))// (3) ["this is a", undefined, undefined]

二、filter [es5]

不改變原數組
須要一個函數做爲參數, 依次便利每個值,根據返回值生成新數組
返回真值 便利到的元素添加至新數組github

console.log([ , 1, '', 2, undefined, 3, null, 4, 0, false, 5, true, 6, new Date()].filter((elem, index) => {
    console.log(elem, index)
    return elem
})) // [1, 2, 3, 4, 5, true, 6, Tue Nov 28 2017 08:29:52 GMT+0800 (中國標準時間)]

三、every [es5] some [es5]

語言太蒼白,show you code
數組的every,和some方法,可參考下面兩個函數實現的功能數組

const every = (fun, arr) => {
    for (let i = 0; i = arr.length; i ++) {
        if (!fun(arr[i], i)) return false    // 有結果爲false, 當即返回false,再也不繼續遍歷
    }
}
const some = (fun, arr) => {
    for (let i = 0; i < arr.length; i ++) {
        if (fun(arr[i], i)) return true      // 有結果爲true, 當即返回true,再也不繼續遍歷
    }
}
[0,1,2,3,4].filter(function (i) {if (i < 2){return 1}})  //[0, 1]

四、reduce [es5] reduceRight [es5]

功能描述參考下面代碼函數

const reduce = (fun, arr, start) => {
    arr = arr.slice()
    start = start === undefined ? arr.shift() : start
    for (let i = 0; i < arr.length; i++) {   // 從左往右
        start = fun(start, arr[i])
    }
    return start
}
const reduceRight = (fun, arr, start) => {
    arr = arr.slice()
    start = start === undefined ? arr.pop() : start
    for (let i = arr.length - 1; i >= 0; i--) {   // 從右往左
        start = fun(start, arr[i])
    }
    return start
}

五、indexOf

返回某個指定的變量在數組中首次出現的位置this

const a = {}
const b = [0, {}, 2, 3, '4', 4, 5, a, 4]
console.log(b.indexOf(a)) // 7
console.log(b.indexOf(4)) // 5
console.log(b.indexOf(4, '6')) // 8
console.log(b.indexOf('4')) // 4

六、lastIndexOf

返回某個指定的變量在數組中最後一次出現的位置es5

const a = {}
const b = [0, {}, 2, 3, '4', 4, 5, a, 4]
console.log(b.lastIndexOf(a)) // 7
console.log(b.lastIndexOf(4)) // 8
console.log(b.lastIndexOf(4, '6')) // 5
console.log(b.lastIndexOf('4')) // 4

es3部分

一、join [es3]

將數組拼接爲字符串.prototype

const b = [0, {}, 2, 3, '4', 4, 5, 4]
console.log(b.join()) // 0,[object Object],2,3,4,4,5,4
console.log(b.join(',')) // 0,[object Object],2,3,4,4,5,4   同b.join()
console.log(b.join('分割符')) //0分割符[object Object]分割符2分割符3分割符4分割符4分割符5分割符4

const a = [new Date(), null, undefined,[1, 2,3], [1, 2, 3], [[11, 12, 13], [21, 22, {a: [1,2,3]}]], {a: 1}]
console.log(a.join())      //Mon Nov 27 2017 15:39:01 GMT+0800 (中國標準時間),,,1,2,3,1,2,3,11,12,13,21,22,[object Object],[object Object]
console.log(a.toString())  //Mon Nov 27 2017 15:41:00 GMT+0800 (中國標準時間),,,1,2,3,1,2,3,11,12,13,21,22,[object Object],[object Object]
const testelema = new Date()
const testelemb = {}
const testelemc = []
testelema.toString = e => 1
testelemb.toString = e => 2
testelemc.toString = e => 3
console.log([testelema, testelemb, testelemc].join('-----'))   //1-----2-----3


const notfunction = {}
notfunction.toString = 1212
console.log([notfunction].join())  //Uncaught TypeError: Cannot convert object to primitive value

我的猜想,join會依次調用數組內元素的toString方法,並拼接成字符串,沒有toString方法的元素返回空'',相似code

const join = 
    (arr, delimiter = ',') => 
        arr.reduce((last, next) => {
            if (next === null || next === undefined) {
                return last + delimiter
            } else {
                if (typeof next.toString !== 'function') {
                    throw new Error(`Cannot convert $ {typeof next}to primitive value `)
                }
                return last + delimiter + next.toString()
            }
        }, '')
        .replace(delimiter, '')

二、reverse [es3]

將數組中的元素顛倒順序
該方法會直接改變原數組排序

const b = [true,'1',2,3,4,5]
b.reverse()
console.log(b.join())

三、sort [es3]

將數組的元素按照必定規則排序
該方法會直接改變原數組
參數類型必須爲function
無參數的時候數組元素默認按照字母表順序排序.

let b = [0,'a', 3,'3', 4,5,false]
console.log(b.sort().join()) //0,3,3,4,5,a,false

b = [0,'a', 3,'3', 4,5,false]
console.log(b.sort((elema, elemb) => {
    console.log(elema, elemb)
    /*
    * 0 "a"
    * a 3
    * 3 "3"
    * 3 4
    * 4 5
    * 5 false
    */
    console.log(typeof elema, typeof elemb)  //雖然上面打印出的字符串變量有的沒有帶引號,可是類型沒錯
    /*
    * number string
    * string number
    * number string
    * string number
    * number number
    * number boolean
    */
}).join())  //0,a,3,3,4,5,false  若是做爲sort參數的方法,無返回值,則排序結果與不帶參數相同

b = [10,'a',false, '20','11', 4,9]
console.log(b.sort((elema, elemb) => {
    if (typeof elema === 'string' && typeof elemb === 'number') {
        return -1   // 返回小於0的數則 elema在前  elemb在後 
    } else if (typeof elema === 'number' && typeof elemb === 'string') {
        return 1    // 返回大於0的數 則 elema在後  elemb在前
    }
    return 0; // 默認返回0   不加return 0結果同樣
}).join()) // a,10,false,20,11,4,9   將字符串排在數字前面

四、concat [es3]

拼接數組
返回新數組,不改變原數組

const a = [1, 2, {a: 3}]
const b = a.concat([1,2,3,4])
console.log(b) //(7) [1, 2, {…}, 1, 2, 3, 4]
const c = a.concat([[1,2,3,4]])
console.log(c) // (4) [1, 2, {…}, Array(4)]
console.log(a) // (3) [1, 2, {…}]
const d = a.concat() 
console.log(d) // (3) [1, 2, {…}]      可使用concat進行淺拷貝
d[0] = 10
console.log(d) // (3) [10, 2, {…}]
console.log(a) // (3) [1, 2, {…}]
d[2].a = 10
console.log(a[2].a)  //10

五、slice [es3]

返回數組的一個片斷
返回新數組,不改變原數組
使用slice複製數組也是淺拷貝
兩個參數時,包含序號爲前一個參數的元素,不包含序號爲後一個參數的元素
前一個參數默認爲0
後一個參數默認爲數組長度

const a = [0,1,2,3,4,5,6,7]
console.log(a.slice()) // (8) [0, 1, 2, 3, 4, 5, 6, 7]
console.log(a.slice(0)) // (8) [0, 1, 2, 3, 4, 5, 6, 7]
console.log(a.slice(0, a.length)) // (8) [0, 1, 2, 3, 4, 5, 6, 7]
console.log(a.slice(2))  // (6) [2, 3, 4, 5, 6, 7]
console.log(a.slice(2, a.length)) // (6) [2, 3, 4, 5, 6, 7]
console.log(a.slice(2, 3)) // [2]
console.log(a.slice(2, 4)) // (2) [2, 3]
console.log(a.slice(-2))  // (2) [6, 7]
console.log(a.slice(-2, a.length))  // (2) [6, 7]
console.log(a.slice(2, a.length - 1))  //(5) [2, 3, 4, 5, 6]
console.log(a.slice(2, - 1))   // (5) [2, 3, 4, 5, 6]

六、splice [es3]

從數組中刪除元素、插入元素、或者同時完成這倆種操做.
splice直接修改數組

let a = [0,1,2,3,4,5,6,7]
a.splice()
console.log(a)  // (8) [0, 1, 2, 3, 4, 5, 6, 7]
a = [0,1,2,3,4,5,6,7]
a.splice(0)
console.log(a)  // []
a = [0,1,2,3,4,5,6,7]
a.splice(0, a.length)
console.log(a)  // []
a = [0,1,2,3,4,5,6,7]
a.splice(0, 1)
console.log(a)  // []

七、其他經常使用的es3方法這裏就簡單列一下,就不囉嗦了

push和pop
unshift和shift;
toString和toLocaleString

es6部分

一、copyWithin

這是一個我想不到應用場景的方法
大概我之後也不多用到
把數組本身的一部分複製到另外一部分
參考以下代碼

const copyWithin = (arr, target, start = 0, end = arr.length) => {
    const copy = arr.slice()
    start = start < 0 ? (start + arr.length) : start
    end = end < 0 ? (end + arr.length) : end
    for (let i = start; i < end; i ++) {  // 拷貝內容不包括end    end 小與 start 什麼操做都不作且不報錯
        arr[target + i - start] = copy[i]   // copyWithin修改原數組
    }
}

二、find

直接上polyfill

// https://tc39.github.io/ecma262/#sec-array.prototype.find
if (!Array.prototype.find) {
  Object.defineProperty(Array.prototype, 'find', {
    value: function(predicate) {
     // 1. Let O be ? ToObject(this value).
      if (this == null) {
        throw new TypeError('"this" is null or not defined');
      }

      var o = Object(this);

      // 2. Let len be ? ToLength(? Get(O, "length")).
      var len = o.length >>> 0;

      // 3. If IsCallable(predicate) is false, throw a TypeError exception.
      if (typeof predicate !== 'function') {
        throw new TypeError('predicate must be a function');
      }

      // 4. If thisArg was supplied, let T be thisArg; else let T be undefined.
      var thisArg = arguments[1];

      // 5. Let k be 0.
      var k = 0;

      // 6. Repeat, while k < len
      while (k < len) {
        // a. Let Pk be ! ToString(k).
        // b. Let kValue be ? Get(O, Pk).
        // c. Let testResult be ToBoolean(? Call(predicate, T, « kValue, k, O »)).
        // d. If testResult is true, return kValue.
        var kValue = o[k];
        if (predicate.call(thisArg, kValue, k, o)) {
          return kValue;
        }
        // e. Increase k by 1.
        k++;
      }

      // 7. Return undefined.
      return undefined;
    }
  });
}

未完待續

相關文章
相關標籤/搜索