-
Notifications
You must be signed in to change notification settings - Fork 0
第五章:数组
ECMAScript数组中的每一项都可以保存任何类型的数据,而且数组的大小是可以动态调整的,可以随着数据的添加自动增长以容纳新增数据。
创建数组的方式有两种:
###1.第一种使用Array
构造函数,
var m = new Array();
var n = new Array(20); --指定大小
var z = new Array(1, 'XD', true, "", "342");
###2.使用数组字面量表示:
var m = ["M", "Q", "Z"];
var n = []; //空数组
数组的length
属性是可以修改的,因此可以通过修改此属性来实现新增或删除数组中的项:
var m = ["M", "Q", "Z"]
m.length = 10; //那么剩下的项都是undefined
m[m.length] = "W";
m[m.length] = "O";
打印结果:
M, Q, Z, , , , , , , , W, O //直接alert(m);
###5.2.1 检测数组
如何判断一个对象是否是数组可以通过instanceof
来判断:
var arr = [1, "red", true, "", "df"];
if(arr instanceof Array){
alert('OK, is Array');
}
也可以使用isArray()
方法来判断:
var arr = new Array();
if(Array.isArray(arr)){
alert("OK, is Array");
}
isArray()
是ECMAScript5中才有的,所以要IE9+以上才能实现
###5.2.2 转换方法
所有的对象都有toLocaleString()
, toString()
, valueOf()
方法,所以数组也有。
调用toString()
方法会返回所有项通过,
拼接的一个字符串,
调用valueOf()
方法返回的还是数组
var arr = [1, "red", true, "", "df"];
alert(arr.toString()); //1, red, true, , df
alert(arr.valueOf()); //1, red, true, , df
alert(arr); //1, red, true, , df
valueOf()方法不是返回数组吗?为什么这里也还是字符串,使用为alert();只接受字符串,所以他会默认调用数组的toString()方法。
有时候并不想通过,
来分割,而是想通过其他字符分割,可以使用join()
操作:
var arr = [1, "red", true, "", "df"];
alert(arr.join("--")); //1--red--true----df
alert(arr.join()); //1,red,true,,df
###5.2.3 栈方法
栈是一种LIFO(last in first out, 后进先出)的数据结构。
栈中的插入叫推入 push()
, 推入的方法push()
可以接受任意数量的参数,把他们逐个添加到数组的末尾,然后返回数组的长度。
移除叫弹出pop()
, 弹出的方法pop()
则从数组末尾移除最后一项,返回移除的项。 而ECMAScript可以使数组想栈一样使用,
var m = new Array();
var count = m.push("W", "M", "Z");
alert(count); //3
var item = m.pop();
alert(item); //Z
###5.2.4 队列方法
队列的数据结构是FIFO(first in first out, 先进先出),队列在末尾添加项,在列表前端移除项。 由于push()
是向数组末尾添加项的方法,因此模拟队列只需一个从数组前端取得项的方法。
shift()
它能够移除数组中的第一个项并返回该项。
var m = new Array();
var count = m.push("W", "M", "Z");
alert(count);
var item = m.shift();
alert(item);
ECMAScript还为数组提供了一个unshift()
方法,与shift()
方法用途相反,他能在数组前端添加任意个项并返回新数组的长度。
var m = new Array("O", "P");
var count = m.unshift("W", "M", "Z");
alert(m); //W, M, Z, O, P
###5.2.5 重排序方法
数组中已经存在两个可以直接用来重排序的方法:reverse()
, sort()
.
1.reverse()
会反转数组项的顺序:
var m = new Array("O", 1, true, "32", "X");
alert(m.reverse()); //X, 32, true, 1, O
2.sort()
按升序排列数组项--即最小的在前面。sort()方法会调用每个数组项的toString()
方法然后比较字符串,所以即使数组中都是数字比较的也都是字符串。
var m = new Array(0, 1, 5, 10, 15, 20);
alert(m.sort()); //0, 1, 10, 15, 20, 5
所以有时候直接使用sort()
并不能满足我们的要求。不过可以给sort()
传递一个比较函数做参数:
var m = new Array(0, 1, 5, 10, 15, 20);
function compare(value1, value2){
if(value1 < value2){
return -1;
}else if(value1 > value2){
return 1;
}else{
return 0;
}
}
alert(m.sort(compare)); //0, 1, 5, 10, 15, 20
如果想倒序只要改下>, <
的位置;
当然,如果整个数组里面都是数字,比较函数可以这样写:
function compare(value1, value2){
return value1 - value2;
}
###5.2.6 操作方法
####1.concat()
此方法可以基于当前数组中的所有项创建一个新数组。
var m = new Array(0, 1, 5, 10);
var z = m.concat();
alert(z); //0, 1, 5, 10
var n = m.concat("yellow", ["black", true]);
alert(n); //0, 1, 5, 10, yellow, black, true
如果没有参数的情况下,他只是简单的复制当前数组。如果参数是一个或多个数组或数值,那么就添加到原有数组后面成立一个新的数组。
####2.slice()
它能够基于当前数组中的一或多个项创建一个新数组。
var m = new Array(0, 1, 5, 10, 20, 34);
var z = m.slice();
alert(z); //0, 1, 5, 10, 20, 34
var n = m.slice(2);
alert(n); //5, 10, 20, 34
var v = m.slice(2, 4);
alert(v); //5, 10
上面的例子就可以看出slice()
方法的使用,最多两个参数,索引从0开始。当然也会有下面这种情况:
var m = new Array(0, 1, 5, 10, 20, 34);
var z = m.slice(-4, -1);
alert(z); //5, 10, 20
如果参数是负数的话,则用数组的长度加上该数来确定相应的位置,所以上面的slice(-4, -1)相当于slice(2, 5);
####3.splice()
此方法用于向数组中部插入项,大致有三种用法:
a.删除:可以删除任意数量的项,只需指定2个参数:要删除的第一项的位置和要删除的项数, 例如:splice(0, 2)会删除数组中的前两项。
b.插入:可以向指定位置插入任意数量的项,只需提供三个即以上的参数:起始位置, 要删除的项数, 要插入的项数; 例如:splice(2, 0, "yellow", "234")会从当前数组的位置2开始插入两个项;
c.替换:其实替换就是插入方式的变形,如果我刚才的例子:splice(2, 2, "yellow", "234")就会从位置2的地方删除2个项再插入两个项;
splice()
方法始终都会返回一个数组,该数组中包含从原始数组中删除的项,如果没有删除就返回一个空数组。
var m = new Array(0, 1, 5, 10, 20, 34);
var z = m.splice(2, 0, "yellow", "234");
alert(m); //0, 1, yellow, 234, 5, 10, 20, 34
alert(z); //空,啥都没有
###5.2.7 位置方法
ECMAScript5为数组实例添加了两个位置方法:indexOf()
, lastIndexOf()
.这两个方法都接受两个参数:要查找的项和表示查找起点位置的索引(这个可选)。如果找到就返回在数组中的位置,没有就返回-1;
var m = new Array(0, 1, 5, 10, 20, 34);
var z = m.indexOf(5);
alert(z); //2
var n = m.indexOf(5, 3); //从第四个位置开始查找5
alert(n); //-1
这两个方法在查找的时候使用的是全相等(===)!
###5.2.8 迭代方法
EMCAScript5为数组定义了5个迭代方法,每个方法都接受两个参数:要在每一项上运行的函数和运行该函数的作用域对象(这个可选)--影响this的值;array.xxx(callback[, thisObject]);
。而传入这些方法中的函数都会接受三个参数:数组项的值, 该项的索引, 数组对象本身。
a.
every()
:对数组中的每一项运行给定函数,如果该函数对每一项都返回true,则返回true;这点有点if里面的and
,
b.
filter()
:对数组中的每一项运行给定函数,返回该函数会返回true的项组成的数组; 在函数里面的判断如果项成立就添加到新数组里,然后返回新数组。
c.
forEach()
:对数组中的每一项运行给定函数,这个方法没有返回值。
d.
map()
:对数组中的每一项运行给定函数,返回每次函数调用的结果组成的数组。
e.
some()
:对数组中的每一项运行给定函数,如果该函数对任一项返回true,则返回true,有点类似if里面的or
;
例如:
var m = new Array(0, 1, 5, 10, 20, 34);
var z = m.every(function(item, index, arr){
return (item > 10); //要全部都成立,才返回true
});
alert(z); //false
var n = m.some(function(item, index, arr){
return (item > 10); //只要一个成立就返回true
});
alert(n); //true
var l = m.filter(function(item, index, arr){
return (item > 10); //所有大于10的项,成立一个新数组
});
alert(l); //20, 34
var p = m.map(function(item, index, arr){
return (item * 10); //所有的项的结果成立一个新数组
});
alert(p); //0, 10, 50, 100, 200, 340
###5.2.9 归并方法
ECMAScript新增了两个归并数组的方法:reduce()
, reduceRight()
.这两个方法都会迭代数组中所有的项,然后构建一个最终返回的值,不过一个从左到右一个相反。
var m = new Array("B", "C", "D", "E", "F");
var z = m.reduce(function(prev, cur, index, arr){
return prev + cur; //第一次prev是B, cur是C, 第二次prev是BC
});
alert(z); //BCDEF
var n = m.reduce(function(prev, cur, index, arr){
return prev + cur;
}, "A"); //第二个参数是归并基础的初始化值
alert(n); //ABCDEF
reduce()
传递两个参数:一个在每一项上调用的函数和作为归并基础的初始化值(这个可选).传入函数接收4个参数:前一个值, 当前值, 项的索引, 数组对象。