Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

【js】细说数组 #3

Open
katara1109 opened this issue Dec 11, 2020 · 0 comments
Open

【js】细说数组 #3

katara1109 opened this issue Dec 11, 2020 · 0 comments

Comments

@katara1109
Copy link
Owner

数组

[[toc]]

0、数组的方法大合集

::: tip

含义 方法 返回值 改变原数组
删除 pop() 删除项 yes
删除 shift() 删除项 yes
截取 slice() 删除项 no
删除 splice() 新数组 yes
删除 length / yes
添加 push() length yes
添加 unshift() length yes
添加 concat() 新数组 no
添加 splice() 删除项 yes
添加 [...array,...array1] 新数组 no
添加 Array.prototype.push.apply(arr1,arr2) length yes
splice() 新数组 yes
排序 sort() 新数组 yes
反向 reverse() 新数组 yes
递归 reduce() 计算的值 no
递归 reduceRight() 计算的值 no
查位置 indexof() 位置 no
反向查位置 lastIndexOf() 位置 no
找到第一个符合的成员 find() 成员 no
找到第一个符合的位置 findIndex() 位置 no
包含值否 includes() boolean no
计算 map() 计算后 no
过滤 filter() 满足条件的 no
判断都 every() boolean no
判断有 some() boolean no
遍历 forEach() return的值 no
string->arry split() array no
arry->string join() string no
arry->string toString() string no
arry->string toLocalString() string no
obj-->arry for ..in 循环赋值法 / /
obj-->arry Array.from() 新数组 /
number-->arry Array.of() 新数组 /
填充/替换 fill(值,start,end) 新数组 yes
键值对 entries() 键值对 no
建值 keys() 建值 no
建名 values() 建名 no
指定位置的成员复制到其他位置 copyWithin(target,start,end) 新数组 yes

这是一个详情块,在 IE / Edge 中不生效
:::

一、对数组的增 删 改 查:

❤️

1.1数组的增加

array.push()   向数组末尾添加元素,返回的是添加后新数组的长度,原有数组改变
array.unshift()  向数组开头添加元素,返回的是添加后新数组的长度,原有数组改变
array.splice(n,m,x)   从索引n开始删除m个元素,然后插入元素x,把删除的内容当做新数组返回,原有数组改变。作添加使用,将m设置为0 即可。
array.concat(),拼接数组。返回拼接之后的数组,原数组不改变。
[...arr1, ...arr2, ...arr3] 解构数组,数组与数组的合并,返回合并的数组,原数组不改变。
Array.prototype.push.apply(arr1,arr2);----将arr2追加到arr1中,返回数组的长度,改变原数组。

clipboard.png

var fruits = ['Apple', 'Banana'];
var newLength = fruits.push('Orange');
// newLength:3; fruits: ["Apple", "Banana", "Orange"]

var newLength = fruits.unshift('Strawberry') // add to the front
//  newLength:4; fruits: ["Strawberry", "Apple", "Banana", "Orange"]


1.2 数组的删除

array.pop() 删除数组的最后一项,返回的是删除的那一项,原有数组改变
array.shift() 删除数组的的第一项,返回的是删除的那一项,原有数组改变
splice(n,m,x) 从索引n开始删除m个元素,然后插入元素x,把删除的内容当做新数组返回,原有数组改变。作删除使用,x不传入数据既可。
slice(n,m) 从索引n开,到索引m 结束 ,返回删除项,原数组不变
length   减小数组的长度,实际是从数组尾部删除元素,改变原数组。
let fruits = ["Strawberry", "Apple", "Banana", "Orange"]
var value = fruits.pop()
// value: Orange; fruits: ["Strawberry", "Apple", "Banana"]

var value = fruits.shift()
// value: Strawberry ; fruits: [ "Apple", "Banana"]

1.3

 其实只有一种 splice(),但delete方法,我个人感觉算修改不属于删除,详情请见实例

1.4

indeOf()
lastIndexOf()
find()
findIndex()
includes()

[1, 4, -5, 10].find((n) => n < 0)    // -5
[1, 4, -5, 10].findIndex((n) => n < 0) // 2
[1, 2, 3].includes(2)     // true

二、数组深浅拷贝

对象和数组的拷贝有两种

浅拷贝即 拷贝了指针指向,当一个对象的值改变会影响另一个对象的值。

深拷贝, 拷贝的是真正的值。2者相互独立,互不干扰。

2.1浅拷贝的方法4种方法

  • slice()
  • concat()
  • 赋值法
  • 遍历

注:concat 和 slice 对一维数组 能算是深拷贝;2维的 是浅拷贝

// slice 法
let a = [1,2,3]
let b= a 
let c = a.slice()

a.pop()

// 最后a  b c 分别是多少
a // [1,2]
b // [1,2]
c = [1,2,3]
// Array.from法
let a = [1,2,3]
let b= a 
let c = Array.from(a)

a.pop()

// 最后a  b c 分别是多少
a // [1,2]
b // [1,2]
c = [1,2,3]
    var  a= [1,2,3,4]
    b= a.concat();
    c=a.concat();
    b[0] = 5;
    c[0] = 6;
    a // [1,2,3,4]
    b // [5,2,3,4]
    c // [6,2,3,4]

    var  aa= [[1,1],[2,2],3,4]
    bb= aa.concat();
    cc=aa.concat();
    bb[1][0] = 5;
    cc[0] = 6;
    aa // [[1,1],[5,2],3,4]
    b // [[1,1],[5,2],3,4]
    c // [6,[5,2],3,4]
var shallowCopy = function(obj) {
    // 只拷贝对象
    if (typeof obj !== 'object') return;
    // 根据obj的类型判断是新建一个数组还是对象
    var newObj = obj instanceof Array ? [] : {};
    // 遍历obj,并且判断是obj的属性才拷贝
    for (var key in obj) {
        if (obj.hasOwnProperty(key)) {
            newObj[key] = obj[key];
        }
    }
    return newObj;
}

2.2 深拷贝的方法5种方法:

一维数组和对象的concat slice法 JSON.parse(JSON.stringify(arr)) 和遍历法 解构赋值法
示例:(前3种毕竟简单,这里也不表述)
解构赋值法:const a1 = [1, 2]; const a2 = [...a1];或者const [...a2] = a1;

var deepCopy = function(obj) {
if (typeof obj !== 'object') return;
var newObj = obj instanceof Array ? [] : {};
for (var key in obj) {
if (obj.hasOwnProperty(key)) {
newObj[key] = typeof obj[key] === 'object' ? deepCopy(obj[key]) : obj[key];
}
}
return newObj;
}

三、数组与字符串 对象的转换

3.1字符串转数组

es5 split(',');
es6 扩展运算符

let hh = 'fh,fed,fd';
hh.split(','); // [fh,fed,fd]

 [...'hello']
 // [ "h", "e", "l", "l", "o" ]

3.2数组转字符串

2.1 toString();
2.2 toLocaleString();
2.3 join(',')
2.4 遍历,然后拼接法
![这里写图片描述](http://img.blog.csdn.net/20180201154816999?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQva2F0YXJhMTEwOQ==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast)

3.3 类似数组对象转数组

  • es5 Array.prototype.slice.call(obj) / [].slice.call(obj)
  • es6 Array.from(obj)

3.4一组值转为数组

es6 Array.of(2,3,4); // [2,3,4]

四、数组去重

[...new Set(arr1)]
这里写图片描述

五、 数组的5个迭代方法----在数组的每一项上运行函数

filter();---返回true项的数组

❤️ map();-----返回运算后的组成的新数组:

因为map生成一个新数组,当你不打算使用返回的新数组却使用map是违背设计初衷的,请用forEach或者for-of替代。
你不该使用map: A)你不打算使用返回的新数组,或/且 B) 你没有从回调函数中返回值。
var new_array = arr.map(function callback(currentValue[, index[, array]]) {
 // Return element for new_array 
}[, thisArg])

every();--每一项都是true,则返回true

❤️ forEach();-----无返回值,不可链式调用

arr.forEach(callback(currentValue [, index [, array]])[, thisArg])

some();----有一项返回true,则返回true

六、并归方法

reduce();

Array的reduce()把一个函数作用在这个Array的[x1, x2, x3...]上,这个函数必须接收两个参数,reduce()把结果继续和序列的下一个元素做累积计算,

[x1, x2, x3, x4].reduce(f) = f(f(f(x1, x2), x3), x4)

var arr = [1, 3, 5, 7, 9];
arr.reduce(function (x, y) {
    return x + y;
}); // 25

reduceRight();反向并归

七 判断数组

2-3种方法

var ss=[];
typeof ss; // object
ss instanceof Array; // true
Array.isArray(ss); // true;

八 将nodeList转换成数组

(2方法)

var elements = document.querySelectorAll("p"); // NodeList var arrayElements = [].slice.call(elements); // Now the NodeList is an array var arrayElements = Array.from(elements); // This is another way of converting

九 数组元素的洗牌

var list = [1,2,3];
list.sort(function() { return Math.random() - 0.5 })); // [2,1,3]
上述的是 投机取巧的方式
真正的数组乱序,请见

function shuffle(a) {
  var length = a.length;
  var shuffled = Array(length);

  for (var index = 0, rand; index < length; index++) {
    rand = ~~(Math.random() * (index + 1));
    if (rand !== index) 
      shuffled[index] = shuffled[rand];
    shuffled[rand] = a[index];
  }

  return shuffled;
}
function shuffle(a) {
  var b = [];

  while (a.length) {
    var index = ~~(Math.random() * a.length);
    b.push(a[index]);
    a.splice(index, 1);
  }

  return b;
}

十.考题

  1. Array.isArray( Array.prototype )

    // true ;because:Array.prototype is an Array

    var a = [0];
    if ([0]) {
      console.log(a == true);
    } else {
      console.log("wut");
    }
    // false ;  
    // because:[0] as a boolean is considered true. Alas, when using it in the comparisons it gets converted in a different way and all goes to hell.
  1. []==[]

    // false;because: == is the spawn of satan.

var ary = Array(3);
ary[0]=2
ary.map(function(elem) { return '1'; });

// [1,empty*2]
[1 < 2 < 3, 3 < 2 < 1]

// [true] // true <3 => 1<3  false < 1 => 0<1 
var a = [1, 2, 3],
    b = [1, 2, 3],
    c = [1, 2, 4]
a ==  b
a === b
a >   c
a <   c

// false false false true ;
// because:字面量相等的数组也不相等.  数组在比较大小的时候按照字典序比较

十一 应用

. 实现扁平化数组

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant