`
abruzzi
  • 浏览: 449307 次
  • 性别: Icon_minigender_1
  • 来自: 西安
社区版块
存档分类
最新评论

JavaScript内核系列 第5章 数组

阅读更多

第五章 数组

JavaScript的数组也是一个比较有意思的主题,虽然名为数组(Array),但是根据数组对象上的方法来看,更像是将很多东西混在在一起的结果。而传统的程序设计语言如C/Java中,数组内的元素需要具有相同的数据类型,而作为弱类型的JavaScript,则没有这个限制,事实上,JavaScript的同一个数组中,可以有各种完全不同类型的元素。

 

方法

描述

concat()  

连接两个或更多的数组,并返回结果。

join()

把数组的所有元素放入一个字符串。元素通过指定的分隔符进行分隔。

pop()

删除并返回数组的最后一个元素。

push()

向数组的末尾添加一个或更多元素,并返回新的长度。

reverse()

颠倒数组中元素的顺序。

shift()

删除并返回数组的第一个元素。

slice()

从某个已有的数组返回选定的元素。

sort()

对数组的元素进行排序。

splice()

删除元素,并向数组添加新元素。

unshift() 

向数组的开头添加一个或更多元素,并返回新的长度。

valueOf()

返回数组对象的原始值。

 

可以看出,JavaScript的数组对象比较复杂,包含有pop,push等类似与栈的操作,又有slice reversesort这样类似与列表的操作。或许正因为如此,JavaScript中的数组的功能非常强大。

5.1数组的特性

数组包括一些属性和方法,其最常用的属性则为lengthlength表示数组的当前长度,与其他语言不同的是,这个变量并非只读属性,比如:

 

var array = new Array(1, 2, 3, 4, 5);
print(array.length);
array.length = 3;
print(array.length);

 

 

运行结果为:

 

5
3
1,2,3

 

注意到最后的print语句的结果是”1,2,3”,原因是对length属性的修改会使得数组后边的元素变得不可用(如果修改后的length比数组实际的长度小的话),所以可以通过设置length属性来将数组元素裁减。

另一个与其他语言的数组不同的是,字符串也可以作为数组的下标(事实上,在JavaScript的数组中,数字下标最终会被解释器转化为字符串,也就是说,所谓的数字下标只不过是看着像数字而实际上是字符的属性名),比如:

 

var stack = new Array();
 
stack['first'] = 3.1415926;
stack['second'] = "okay then.";
stack['third'] = new Date();
 
for(var item in stack){
    print(typeof stack[item]);
}

 

 

运行结果为:


number
string
object

 

在这个例子里,还可以看到不同类型的数据是如何存储在同一个数组中的,这么做有一定的好处,但是在某些场合则可能形成不便,比如我们在函数一章中讨论过的sum函数,sum接受非显式的参数列表,使用这个函数,需要调用者必须为sum提供数字型的列表(当然,字符串无法做sum操作)。如果是强类型语言,则对sum传入字符串数组会被编译程序认为是非法的,而在JavaScript中,程序需要在运行时才能侦测到这一错误。

5.2使用数组

5.2.1 数组的基本方法使用

数组有这样几种方式来创建:

var array = new Array();
var array = new Array(10);//长度
var array = new Array("apple", "borland", "cisco");

 

 

不过,运用最多的为字面量方式来创建,如果第三章中的JSON那样,我们完全可以这样创建数组:

 

var array = [];
var array = ["one", "two", "three", "four"];

 

 

下面我们通过一些实际的小例子来说明数组的使用(主要方法的使用)

向数组中添加元素:

 

var array = [];
 
array.push(1);
array.push(2);
array.push(3);
 
array.push("four");
array.push("five");
 
array.push(3.1415926);

 

 

 前面提到过,JavaScript的数组有列表的性质,因此可以向其中push不同类型的元素,接上例:

 

var len = array.length;
for(var i = 0; i < len; i++){
    print(typeof array[i]);
}

 

 

结果为:


number
number
number
string
string
number

 

弹出数组中的元素:

 

for(var i = 0; i < len; i++){
    print(array.pop());
}
print(array.length);

 

 

运行结果如下,注意最后一个0是指array的长度为0,因为这时数组的内容已经全部弹出:


3.1415926
five
four
3
2
1
0

 

join,连接数组元素为一个字符串:


array = ["one", "two", "three", "four", "five"];
 
var str1 = array.join(",");
var str2 = array.join("|");
 
print(str1);
print(str2);

 

运行结果如下:


one,two,three,four,five
one|two|three|four|five

 

连接多个数组为一个数组:

 

var another = ["this", "is", "another", "array"];
var another2 = ["yet", "another", "array"];
 
var bigArray = array.concat(another, another2);

 

 

结果为:


one,two,three,four,five,this,is,another,array,yet,another,array

 

从数组中取出一定数量的元素,不影响数组本身:


print(bigArray.slice(5,9));

 

结果为:

 

this,is,another,array

 


slice方法的第一个参数为起始位置,第二个参数为终止位置,操作不影响数组本身。下面我们来看splice方法,虽然这两个方法的拼写非常相似,但是功用则完全不同,事实上,splice是一个相当难用的方法:

 

bigArray.splice(5, 2);
 
bigArray.splice(5, 0, "very", "new", "item", "here");

 

第一行代码表示,从bigArray数组中,从第5个元素起,删除2个元素;而第二行代码表示,从第5个元素起,删除0个元素,并把随后的所有参数插入到从第5个开始的位置,则操作结果为:

one,two,three,four,five,very,new,item,here,another,array,yet,another,array

 

我们再来讨论下数组的排序,JavaScript的数组的排序函数sort将数组按字母顺序排序,排序过程会影响源数组,比如:

 

var array = ["Cisio", "Borland", "Apple", "Dell"];
print(array);
array.sort();
print(array);

 

 

执行结果为:

 

Cisio,Borland,Apple,Dell
Apple,Borland,Cisio,Dell

 

这种字母序的排序方式会造成一些非你所预期的小bug,比如:

 

var array = [10, 23, 44, 58, 106, 235];
array.sort();
print(array);

 

 

得到的结果为:

 

10,106,23,235,44,58

 

可以看到,sort不关注数组中的内容是数字还是字母,它仅仅是按照字母的字典序来进行排序,对于这种情况,JavaScript提供了另一种途径,通过给sort函数传递一个函数对象,按照这个函数提供的规则对数组进行排序。

 

function sorter(a, b){
    return a - b;
}
 
var array = [10, 23, 44, 58, 106, 235];
array.sort(sorter);
print(array);

 

 

函数sorter接受两个参数,返回一个数值,如果这个值大于0,则说明第一个参数大于第二个参数,如果返回值为0,说明两个参数相等,返回值小于0,则第一个参数小于第二个参数,sort根据这个返回值来进行最终的排序:

 

10,23,44,58,106,235

 

当然,也可以简写成这样:


array.sort(function(a, b){return a - b;});//正序
array.sort(function(a, b){return b - a;});//逆序

 

5.2.2 删除数组元素

虽然令人费解,但是JavaScript的数组对象上确实没有一个叫做delete或者remove的方法,这就使得我们需要自己扩展其数组对象。一般来说,我们可以扩展JavaScript解释器环境中内置的对象,这种方式的好处在于,扩展之后的对象可以适用于其后的任意场景,而不用每次都显式的声明。而这种做法的坏处在于,修改了内置对象,则可能产生一些难以预料的错误,比如遍历数组实例的时候,可能会产生令人费解的异常。

数组中的每个元素都是一个对象,那么,我们可以使用delete来删除元素吗?来看看下边这个小例子:

 

var array = ["one", "two","three","four"];
//数组中现在的内容为:
//one,two,three,four
//array.length == 4
delete array[2];

 

 

然后,我们再来看看这个数组的内容:

 

one, two, undefined, four
//array.length == 4
 

可以看到,delete只是将数组array的第三个位置上的元素删掉了,可是数组的长度没有改变,显然这个不是我们想要的结果,不过我们可以借助数组对象自身的slice方法来做到。一个比较好的实现,是来自于jQuery的设计者John Resig

 

//Array Remove - By John Resig (MIT Licensed)
Array.prototype.remove = function(from, to) {
    var rest = this.slice((to || from) + 1 || this.length);
    this.length = from < 0 ? this.length + from : from;
    return this.push.apply(this, rest);
};

 

这个函数扩展了JavaScript的内置对象Array,这样,我们以后的所有声明的数组都会自动的拥有remove能力,我们来看看这个方法的用法:

 

var array = ["one", "two", "three", "four", "five", "six"];
print(array);
array.remove(0);//删除第一个元素
print(array);
array.remove(-1);//删除倒数第一个元素
print(array);
array.remove(0,2);//删除数组中下标为0-2的元素(3个)
print(array);

 

 

会得到这样的结果:

 

one,two,three,four,five,six
two,three,four,five,six
two,three,four,five
five

 

也就是说,remove接受两个参数,第一个参数为起始下标,第二个参数为结束下标,其中第二个参数可以忽略,这种情况下会删除指定下标的元素。当然,不是每个人都希望影响整个原型链(原因在下一个小节里讨论),因此可以考虑另一种方式:

 

//Array Remove - By John Resig (MIT Licensed)
Array.remove = function(array, from, to) {
    var rest = array.slice((to || from) + 1 || array.length);
    array.length = from < 0 ? array.length + from : from;
    return array.push.apply(array, rest);
};

 

其操作方式与前者并无二致,但是不影响全局对象,代价是你需要显式的传递需要操作的数组作为第一个参数:

 

var array = ["one", "two", "three", "four", "five", "six"];
Array.remove(array, 0, 2);//删除0, 1, 2三个元素
print(array);

 

 

这种方式,相当于给JavaScript内置的Array添加了一个静态方法。

5.2.3遍历数组

在对象与JSON这一章中,我们讨论了for…in这种遍历对象的方式,这种方式同样适用于数组,比如:

 

var array = [1, 2, 3, 4];
for(var item in array){
    print(array[item]);
}

 

 

将会打印:

 

1
2
3
4

 

但是这种方式并不总是有效,比如我们扩展了内置对象Array,如下:

 

Array.prototype.useless = function(){}

 

然后重复执行上边的代码,会得到这样的输出:

 

1
2
3
4
function(){}

 

设想这样一种情况,如果你对数组的遍历做sum操作,那么会得到一个莫名其妙的错误,毕竟函数对象不能做求和操作。幸运的是,我们可以用另一种遍历方式来取得正确的结果:

 

for(var i = 0, len = array.length; i < len;i++){
    print(array[i]);
}

 

 

这种for循环如其他很多语言中的写法一致,重要的是,它不会访问哪些下标不是数字的元素,如上例中的function,这个function的下标为useless,是一个字符串。从这个例子我们可以看出,除非必要,尽量不要对全局对象进行扩展,因为对全局对象的扩展会造成所有继承链上都带上“烙印”,而有时候这些烙印会成为滋生bug的温床。

 

附:由于作者本身水平有限,文中难免有纰漏错误等,或者语言本身有不妥当之处,欢迎及时指正,提出建议,参与讨论,谢谢大家!

分享到:
评论
28 楼 jwtiger 2010-04-26  
楼主不要操之过急 慢工出细活 出一章就要精一章 保质保量才是王道
27 楼 abruzzi 2010-04-26  
accphc 写道
发现数组是数组、链表、栈、HashMap的结合体

对,它就是这么一结合体。所以要单独开一章出来讨论。如果像传统的语言中,数组作为一个内嵌的数据结构存在的话,就简单多了,只需要说“JavaScript数组跟其他语言中的数组类似”即可,呵呵。
26 楼 accphc 2010-04-26  
发现数组是数组、链表、栈、HashMap的结合体
25 楼 mengqingyu 2010-04-26  
<div class="quote_title">abruzzi 写道</div>
<div class="quote_div">
<h2>
<a name="_Toc259883914"><span>第五章</span> </a><span><span>数组</span></span> </h2>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span lang="EN-US">JavaScript</span><span>的数组也是一个比较有意思的主题,虽然名为数组</span><span lang="EN-US">(Array)</span><span>,但是根据数组对象上的方法来看,更像是将很多东西混在在一起的结果。而传统的程序设计语言如</span><span lang="EN-US">C/Java</span><span>中,数组内的元素需要具有相同的数据类型,而作为弱类型的</span><span lang="EN-US">JavaScript</span><span>,则没有这个限制,事实上,</span><span lang="EN-US">JavaScript</span><span>的同一个数组中,可以有各种完全不同类型的元素。</span></p>
<p class="MsoNormal"><span lang="EN-US"> </span></p>
<table class="MsoNormalTable" style="border-collapse: collapse; border: none;" border="1" cellspacing="0" cellpadding="0"><tbody>
<tr>
<td style="width: 213.05pt; border-left: none; border-right: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span>方法</span></strong></p>
</td>
<td style="width: 213.05pt; border-left: none; border-right: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span>描述</span></strong></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">concat()<span>   </span></span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>连接两个或更多的数组,并返回结果。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">join()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>把数组的所有元素放入一个字符串。元素通过指定的分隔符进行分隔。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">pop()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>删除并返回数组的最后一个元素。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">push()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>向数组的末尾添加一个或更多元素,并返回新的长度。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">reverse()<span> </span></span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>颠倒数组中元素的顺序。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">shift()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>删除并返回数组的第一个元素。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">slice()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>从某个已有的数组返回选定的元素。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">sort()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>对数组的元素进行排序。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">splice()</span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>删除元素,并向数组添加新元素。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">unshift()<span>  </span></span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>向数组的开头添加一个或更多元素,并返回新的长度。</span></p>
</td>
</tr>
<tr>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><strong><span style="color: #365f91;">valueOf()<span> </span></span></strong></p>
</td>
<td style="width: 213.05pt; border: none; padding: 0cm 5.4pt 0cm 5.4pt;" width="284" valign="top">
<p class="MsoNormal"><span>返回数组对象的原始值。</span></p>
</td>
</tr>
</tbody></table>
<p class="MsoNormal"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>可以看出,</span><span lang="EN-US">JavaScript</span><span>的数组对象比较复杂,包含有</span><span lang="EN-US">pop,push</span><span>等类似与栈的操作,又有</span><span lang="EN-US">slice</span><span>,</span><span lang="EN-US"> reverse</span><span>,</span><span lang="EN-US">sort</span><span>这样类似与列表的操作。或许正因为如此,</span><span lang="EN-US">JavaScript</span><span>中的数组的功能非常强大。</span></p>
<h3>
<a name="_Toc259883915"><span lang="EN-US">5.1</span></a><span><span>数组的特性</span></span> </h3>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>数组包括一些属性和方法,其最常用的属性则为</span><span lang="EN-US">length</span><span>,</span><span lang="EN-US">length</span><span>表示数组的当前长度,与其他语言不同的是,这个变量并非只读属性,比如:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = new Array(1, 2, 3, 4, 5); print(array.length); array.length = 3; print(array.length);<span style="font-size: small;"><span style="font-size: 13px;"> </span></span>
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>运行结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"> </p>
<p> </p>
<div class="quote_div">5<br>3<br>1,2,3</div>
<p class="MsoNormal"> </p>
<p class="MsoNormal"><span>注意到最后的</span><span lang="EN-US">print</span><span>语句的结果是</span><span lang="EN-US">”1,2,3”</span><span>,原因是对</span><span lang="EN-US">length</span><span>属性的修改会使得数组后边的元素变得不可用</span><span lang="EN-US">(</span><span>如果修改后的</span><span lang="EN-US">length</span><span>比数组实际的长度小的话</span><span lang="EN-US">)</span><span>,所以可以通过设置</span><span lang="EN-US">length</span><span>属性来将数组元素裁减。</span></p>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>另一个与其他语言的数组不同的是,字符串也可以作为数组的下标</span><span lang="EN-US">(</span><span>事实上,在</span><span lang="EN-US">JavaScript</span><span>的数组中,数字下标最终会被解释器转化为字符串,也就是说,所谓的数字下标只不过是看着像数字而实际上是字符的属性名</span><span lang="EN-US">)</span><span>,比如:</span></p>
<p class="MsoNormal"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var stack = new Array(); stack['first'] = 3.1415926; stack['second'] = "okay then."; stack['third'] = new Date(); for(var item in stack){ print(typeof stack[item]); }
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>运行结果为:</span></p>
<p class="MsoNormal"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
<div class="quote_div">number<br>string<br>object</div>
<p> </p>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>在这个例子里,还可以看到不同类型的数据是如何存储在同一个数组中的,这么做有一定的好处,但是在某些场合则可能形成不便,比如我们在函数一章中讨论过的</span><span lang="EN-US">sum</span><span>函数,</span><span lang="EN-US">sum</span><span>接受非显式的参数列表,使用这个函数,需要调用者必须为</span><span lang="EN-US">sum</span><span>提供数字型的列表</span><span lang="EN-US">(</span><span>当然,字符串无法做</span><span lang="EN-US">sum</span><span>操作</span><span lang="EN-US">)</span><span>。如果是强类型语言,则对</span><span lang="EN-US">sum</span><span>传入字符串数组会被编译程序认为是非法的,而在</span><span lang="EN-US">JavaScript</span><span>中,程序需要在运行时才能侦测到这一错误。</span></p>
<h3>
<a name="_Toc259883916"><span lang="EN-US">5.2</span></a><span><span>使用数组</span></span> </h3>
<h4>
<a name="_Toc259883917"><span lang="EN-US">5.2.1 </span></a><span><span>数组的基本方法使用</span></span> </h4>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>数组有这样几种方式来创建:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = new Array(); var array = new Array(10);//长度 var array = new Array("apple", "borland", "cisco");
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left; text-indent: 21.0pt;" align="left"><span>不过,运用最多的为字面量方式来创建,如果第三章中的</span><span style="font-size: 10.0pt;" lang="EN-US">JSON</span><span>那样,我们完全可以这样创建数组:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = []; var array = ["one", "two", "three", "four"];
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>下面我们通过一些实际的小例子来说明数组的使用</span><span style="font-size: 10.0pt;" lang="EN-US">(</span><span>主要方法的使用</span><span style="font-size: 10.0pt;" lang="EN-US">)</span><span>:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>向数组中添加元素:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = []; array.push(1); array.push(2); array.push(3); array.push("four"); array.push("five"); array.push(3.1415926);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> <span style="font-family: Verdana, Arial, Helvetica, sans-serif; font-size: 12px;"><span>前面提到过,</span><span style="font-size: 10.0pt;" lang="EN-US">JavaScript</span><span>的数组有列表的性质,因此可以向其中</span><span style="font-size: 10.0pt;" lang="EN-US">push</span><span>不同类型的元素,接上例:</span></span></span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var len = array.length; for(var i = 0; i &lt; len; i++){ print(typeof array[i]); }
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
<div class="quote_div">number<br>number<br>number<br>string<br>string<br>number</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>弹出数组中的元素:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>for(var i = 0; i &lt; len; i++){ print(array.pop()); } print(array.length);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>运行结果如下,注意最后一个</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>是指</span><span style="font-size: 10.0pt;" lang="EN-US">array</span><span>的长度为</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>,因为这时数组的内容已经全部弹出:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
<div class="quote_div">3.1415926<br>five<br>four<br>3<br>2<br>1<br>0</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US">join</span><span>,连接数组元素为一个字符串:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
array = ["one", "two", "three", "four", "five"]; var str1 = array.join(","); var str2 = array.join("|"); print(str1); print(str2);
<pre></pre>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>运行结果如下:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
<div class="quote_div">one,two,three,four,five<br>one|two|three|four|five</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>连接多个数组为一个数组:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var another = ["this", "is", "another", "array"]; var another2 = ["yet", "another", "array"]; var bigArray = array.concat(another, another2);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
<div class="quote_div">one,two,three,four,five,this,is,another,array,yet,another,array</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>从数组中取出一定数量的元素,不影响数组本身:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
print(bigArray.slice(5,9));
<pre></pre>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #0000c8; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>
<div class="quote_div">this,is,another,array</div>
</strong></p>
<p> </p>
<p><strong><span style="font-weight: normal;"><br></span></strong></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US">slice</span><span>方法的第一个参数为起始位置,第二个参数为终止位置,操作不影响数组本身。下面我们来看</span><span style="font-size: 10.0pt;" lang="EN-US">splice</span><span>方法,虽然这两个方法的拼写非常相似,但是功用则完全不同,事实上,</span><span style="font-size: 10.0pt;" lang="EN-US">splice</span><span>是一个相当难用的方法:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p> </p>
bigArray.splice(5, 2); bigArray.splice(5, 0, "very", "new", "item", "here");
<pre></pre>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>第一行代码表示,从</span><span style="font-size: 10.0pt;" lang="EN-US">bigArray</span><span>数组中,从第</span><span style="font-size: 10.0pt;" lang="EN-US">5</span><span>个元素起,删除</span><span style="font-size: 10.0pt;" lang="EN-US">2</span><span>个元素;而第二行代码表示,从第</span><span style="font-size: 10.0pt;" lang="EN-US">5</span><span>个元素起,删除</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>个元素,并把随后的所有参数插入到从第</span><span style="font-size: 10.0pt;" lang="EN-US">5</span><span>个开始的位置,则操作结果为:</span></p>
<div class="quote_div">one,two,three,four,five,very,new,item,here,another,array,yet,another,array</div>
<p class="MsoNormal" style="text-align: left;" align="left"> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>我们再来讨论下数组的排序,</span><span lang="EN-US">JavaScript</span><span>的数组的排序函数</span><span lang="EN-US">sort</span><span>将数组按字母顺序排序,排序过程会影响源数组,比如:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><strong><span style="font-size: 10.0pt;" lang="EN-US"> </span></strong></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = ["Cisio", "Borland", "Apple", "Dell"]; print(array); array.sort(); print(array);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>执行结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"> </p>
<p> </p>
<div class="quote_div">Cisio,Borland,Apple,Dell<br>Apple,Borland,Cisio,Dell</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>这种字母序的排序方式会造成一些非你所预期的小</span><span style="font-size: 10.0pt;" lang="EN-US">bug</span><span>,比如:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = [10, 23, 44, 58, 106, 235]; array.sort(); print(array);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>得到的结果为:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"> </p>
<p> </p>
<div class="quote_div">10,106,23,235,44,58</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>可以看到,</span><span style="color: black;">sort</span><span>不关注数组中的内容是数字还是字母,它仅仅是按照字母的字典序来进行排序,对于这种情况,</span><span style="color: black;">JavaScript</span><span>提供了另一种途径,通过给</span><span style="color: black;">sort</span><span>函数传递一个函数对象,按照这个函数提供的规则对数组进行排序。</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>function sorter(a, b){ return a - b; } var array = [10, 23, 44, 58, 106, 235]; array.sort(sorter); print(array);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>函数</span><span style="font-size: 10.0pt;" lang="EN-US">sorter</span><span>接受两个参数,返回一个数值,如果这个值大于</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>,则说明第一个参数大于第二个参数,如果返回值为</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>,说明两个参数相等,返回值小于</span><span style="font-size: 10.0pt;" lang="EN-US">0</span><span>,则第一个参数小于第二个参数,</span><span style="font-size: 10.0pt;" lang="EN-US">sort</span><span>根据这个返回值来进行最终的排序:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"> </p>
<p> </p>
<div class="quote_div">10,23,44,58,106,235</div>
<p> </p>
<p class="MsoNormal" style="text-align: left;" align="left"><span>当然,也可以简写成这样:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: small;"><span style="font-size: 13px;"><br></span></span></p>
<p> </p>
array.sort(function(a, b){return a - b;});//正序 array.sort(function(a, b){return b - a;});//逆序
<pre></pre>
<p> </p>
<h4>
<a name="_Toc259883918"><span lang="EN-US">5.2.2 </span></a><span><span>删除数组元素</span></span> </h4>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>虽然令人费解,但是</span><span lang="EN-US">JavaScript</span><span>的数组对象上确实没有一个叫做</span><span lang="EN-US">delete</span><span>或者</span><span lang="EN-US">remove</span><span>的方法,这就使得我们需要自己扩展其数组对象。一般来说,我们可以扩展</span><span lang="EN-US">JavaScript</span><span>解释器环境中内置的对象,这种方式的好处在于,扩展之后的对象可以适用于其后的任意场景,而不用每次都显式的声明。而这种做法的坏处在于,修改了内置对象,则可能产生一些难以预料的错误,比如遍历数组实例的时候,可能会产生令人费解的异常。</span></p>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>数组中的每个元素都是一个对象,那么,我们可以使用</span><span lang="EN-US">delete</span><span>来删除元素吗?来看看下边这个小例子:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><strong><span style="font-size: 10.0pt;" lang="EN-US"> </span></strong></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><strong></strong></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = ["one", "two","three","four"]; //数组中现在的内容为: //one,two,three,four //array.length == 4 delete array[2];
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>然后,我们再来看看这个数组的内容:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<div class="quote_div">one, two, undefined, four<br>//array.length == 4</div>
 
<p class="MsoNormal"><span>可以看到,</span><span lang="EN-US">delete</span><span>只是将数组</span><span lang="EN-US">array</span><span>的第三个位置上的元素删掉了,可是数组的长度没有改变,显然这个不是我们想要的结果,不过我们可以借助数组对象自身的</span><span lang="EN-US">slice</span><span>方法来做到。一个比较好的实现,是来自于</span><span lang="EN-US">jQuery</span><span>的设计者</span><span lang="EN-US">John Resig</span><span>:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #3f7f5f; font-size: small;"></span></p>
//Array Remove - By John Resig (MIT Licensed) Array.prototype.remove = function(from, to) { var rest = this.slice((to || from) + 1 || this.length); this.length = from &lt; 0 ? this.length + from : from; return this.push.apply(this, rest); };
<pre></pre>
<p> </p>
<p class="MsoNormal"><span>这个函数扩展了</span><span style="font-size: 10.0pt;" lang="EN-US">JavaScript</span><span>的内置对象</span><span style="font-size: 10.0pt;" lang="EN-US">Array</span><span>,这样,我们以后的所有声明的数组都会自动的拥有</span><span style="font-size: 10.0pt;" lang="EN-US">remove</span><span>能力,我们来看看这个方法的用法:</span></p>
<p class="MsoNormal"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = ["one", "two", "three", "four", "five", "six"]; print(array); array.remove(0);//删除第一个元素 print(array); array.remove(-1);//删除倒数第一个元素 print(array); array.remove(0,2);//删除数组中下标为0-2的元素(3个) print(array);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>会得到这样的结果:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; font-size: small;"></span></p>
<div class="quote_div">one,two,three,four,five,six<br>two,three,four,five,six<br>two,three,four,five<br>five</div>
<p> </p>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>也就是说,</span><span lang="EN-US">remove</span><span>接受两个参数,第一个参数为起始下标,第二个参数为结束下标,其中第二个参数可以忽略,这种情况下会删除指定下标的元素。当然,不是每个人都希望影响整个原型链</span><span lang="EN-US">(</span><span>原因在下一个小节里讨论</span><span lang="EN-US">)</span><span>,因此可以考虑另一种方式:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #3f7f5f; font-size: small;"></span></p>
//Array Remove - By John Resig (MIT Licensed) Array.remove = function(array, from, to) { var rest = array.slice((to || from) + 1 || array.length); array.length = from &lt; 0 ? array.length + from : from; return array.push.apply(array, rest); };
<pre></pre>
<p> </p>
<p class="MsoNormal"><span>其操作方式与前者并无二致,但是不影响全局对象,代价是你需要显式的传递需要操作的数组作为第一个参数:</span></p>
<p class="MsoNormal"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = ["one", "two", "three", "four", "five", "six"]; Array.remove(array, 0, 2);//删除0, 1, 2三个元素 print(array);
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>这种方式,相当于给</span><span lang="EN-US">JavaScript</span><span>内置的</span><span lang="EN-US">Array</span><span>添加了一个静态方法。</span></p>
<h4>
<a name="_Toc259883919"><span lang="EN-US">5.2.3</span></a><span><span>遍历数组</span></span> </h4>
<p class="MsoNormal" style="text-indent: 21.0pt;"><span>在对象与</span><span lang="EN-US">JSON</span><span>这一章中,我们讨论了</span><span lang="EN-US">for…in</span><span>这种遍历对象的方式,这种方式同样适用于数组,比如:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><strong><span style="font-size: 10.0pt;" lang="EN-US"> </span></strong></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>var array = [1, 2, 3, 4]; for(var item in array){ print(array[item]); }
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>将会打印:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-size: 10.0pt;" lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; font-size: small;"></span></p>
<div class="quote_div">1<br>2<br>3<br>4</div>
<p> </p>
<p class="MsoNormal"><span>但是这种方式并不总是有效,比如我们扩展了内置对象</span><span lang="EN-US">Array</span><span>,如下:</span></p>
<p class="MsoNormal"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; font-size: small;"></span></p>
Array.prototype.useless = function(){}
<pre></pre>
<p> </p>
<p class="MsoNormal"><span>然后重复执行上边的代码,会得到这样的输出:</span></p>
<p class="MsoNormal"><span lang="EN-US"> </span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; font-size: small;"></span></p>
<div class="quote_div">1<br>2<br>3<br>4<br>function(){}</div>
<p> </p>
<p class="MsoNormal"><span>设想这样一种情况,如果你对数组的遍历做</span><span lang="EN-US">sum</span><span>操作,那么会得到一个莫名其妙的错误,毕竟函数对象不能做<em>求和</em>操作。幸运的是,我们可以用另一种遍历方式来取得正确的结果:</span></p>
<p class="MsoNormal" style="text-align: left;" align="left"><strong><span style="font-size: 10.0pt;" lang="EN-US"> </span></strong></p>
<p class="MsoNormal" style="text-align: left;" align="left"><span style="font-family: 'Courier New'; color: #7f0055; font-size: small;"><span style="font-size: 13px;"><strong></strong></span></span></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong></strong></p>
<p><strong>for(var i = 0, len = array.length; i &lt; len;i++){ print(array[i]); }
<pre></pre>
</strong></p>
<p> </p>
<p> </p>
<p class="MsoNormal"><span>这种</span><span lang="EN-US">for</span><span>循环如其他很多语言中的写法一致,重要的是,它不会访问哪些下标不是数字的元素,如上例中的</span><span lang="EN-US">function,</span><span>这个</span><span lang="EN-US">function</span><span>的下标为</span><span lang="EN-US">useless,</span><span>是一个字符串。从这个例子我们可以看出,除非必要,尽量不要对全局对象进行扩展,因为对全局对象的扩展会造成所有继承链上都带上“烙印”,而有时候这些烙印会成为滋生</span><span lang="EN-US">bug</span><span>的温床。</span></p>
<p class="MsoNormal"> </p>
<p class="MsoNormal"><span style="line-height: 18px; font-family: Arial, sans-serif, Helvetica, Tahoma;"><strong style="font-weight: bold;">附:由于作者本身水平有限,文中难免有纰漏错误等,或者语言本身有不妥当之处,欢迎及时指正,提出建议,参与讨论,谢谢大家!</strong></span></p>
</div>
<p> </p>
24 楼 mengqingyu 2010-04-26  
楼主  讲的很不错 支持一下
23 楼 zhangjf108 2010-04-26  
不错,很好的东西!
22 楼 ccyingfu 2010-04-26  
写的好极了。
21 楼 s79 2010-04-25  
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标(事实上

Array也是Object类型,如果本文要介绍Array,就不应该把与Object相关的内容在这里介绍。
如果说给一个Object添加的property能被称为“下标”,如var a=[1,2];a.new="NEW";那么无法解释a.new不能参与到length的计算,不能被a.sort()操作等。

另外不要用for...in遍历数组对象,如果把它当作数组来用,一定要使用for(var i=0;i<a.length;i++)这样的方式,确保得到的每个“元素”都是这个数组的下标。

实际应用中,很少会把数组设计的离散。如果过于离散,就失去了数组的意义,莫不如使用Object容易理解。
20 楼 abruzzi 2010-04-25  
hyj1254 写道
介绍下sort()函数的用法吧(这个问的有点弱了

关于数组的排序部分已经更新,可以看看,谢谢你的提醒!
19 楼 abruzzi 2010-04-25  
cryolite 写道
length修改后会影响数组的实际大小,这个得提一下

本来准备在5.1小节上讲的,结果举的例子少些了些东西:
var array = new Array(1, 2, 3, 4, 5);  
print(array.length);  
array.length = 3;  
print(array.length);
 
 
运行结果为:

引用

5
3
1,2,3


不知道大家有没有注意到这个1,2,3,其实这个就是修改了length属性之后执行print(array)语句的运行结果,可能排版的时候给删掉了,不好意思。我再修改下。 
18 楼 abruzzi 2010-04-25  
hyj1254 写道
介绍下sort()函数的用法吧(这个问的有点弱了


好的,我在最后加一小节,先整理下,随后再贴上来。
17 楼 cryolite 2010-04-25  
length修改后会影响数组的实际大小,这个得提一下
16 楼 hyj1254 2010-04-25  
介绍下sort()函数的用法吧(这个问的有点弱了
15 楼 abruzzi 2010-04-25  
zhouyrt 写道


呵,数组的数字索引看起来像其它语言的索引,但实际上它会隐式的转换成字符串。亦可参考
http://snandy.iteye.com/blog/284805
http://snandy.iteye.com/blog/407351


嗯,不错,用一个for..in就可以看到了。JavaScript的数组本质上还是键-值这样的形式,而不是一个连续的内存块(C/Java中都是连续的),而是一个散列表。
14 楼 zhouyrt 2010-04-25  
abruzzi 写道
yuyue618 写道
s79 写道
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标……


这句话容易误导初学者。建议更正。


是呀,这时候已经不是下标了吧. 而是对象的属性?


事实上,在JavaScript里,不存在数字下标这个传统上的东西,数字下标和字符串下标都是“JavaScript数组”这种特殊对象的属性,比如:

var array = ["first", "second", "third"];
print(array["0"]);//以字符串0为下标
print(array[0]);//以数字0为下标


会得到相同的结果:

引用

first
first


JavaScript数组其实是将数字转化成字符串,然后将这个字符串作为“数组”对象的属性来进行存取的。说白了,在存取属性上,它跟其他的对象并无二致。


呵,数组的数字索引看起来像其它语言的索引,但实际上它会隐式的转换成字符串。亦可参考
http://snandy.iteye.com/blog/284805
http://snandy.iteye.com/blog/407351



13 楼 abruzzi 2010-04-25  
yuyue618 写道
s79 写道
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标……


这句话容易误导初学者。建议更正。


是呀,这时候已经不是下标了吧. 而是对象的属性?


事实上,在JavaScript里,不存在数字下标这个传统上的东西,数字下标和字符串下标都是“JavaScript数组”这种特殊对象的属性,比如:

var array = ["first", "second", "third"];
print(array["0"]);//以字符串0为下标
print(array[0]);//以数字0为下标


会得到相同的结果:

引用

first
first


JavaScript数组其实是将数字转化成字符串,然后将这个字符串作为“数组”对象的属性来进行存取的。说白了,在存取属性上,它跟其他的对象并无二致。
12 楼 zhouyrt 2010-04-25  
yuyue618 写道
s79 写道
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标……


这句话容易误导初学者。建议更正。


是呀,这时候已经不是下标了吧. 而是对象的属性?


看怎么理解了,用字符串作为下标可称为关联数组。

数组分类:

1、从数组的下标分为索引数组、关联数组

2、从对数据的存储分为静态数组、动态数组

js的数组同时属于索引数组和动态数组,本质上它就是一个对象,js的索引数组并非“连续分配”内存的,因此索引方式并不会带来很高的效率。而c,c++,java中的数组则是连续分配内存的,如果按照c,c++,java中数组的理解,那么js中的关联数组不能称为数组,即使是js中的Array也不能称为数组,因为Array只是具有索引数字,但并非“连续分配”内存的。
11 楼 whaosoft 2010-04-25  
不错 不错 全部复制走
10 楼 yuyue618 2010-04-25  
s79 写道
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标……


这句话容易误导初学者。建议更正。


是呀,这时候已经不是下标了吧. 而是对象的属性?
9 楼 s79 2010-04-25  
引用
另一个与其他语言的数组不同的是,字符串也可以作为数组的下标……


这句话容易误导初学者。建议更正。

相关推荐

    javascript入门笔记

    Javascript Basic 1、Javascript 概述(了解) Javascript,简称为 JS,是一款能够运行在 JS解释器/引擎 中的脚本语言 JS解释器/引擎 是JS的运行环境: 1、独立安装的JS解释器 - NodeJS 2、嵌入在浏览器中的JS...

    12_JavaScript笔记.pdf

    不同的浏览器可能采用不同的内核来解析和执行JavaScript,例如IE系列使用Trident内核,Safari和早期的Chrome使用WebKit,Chrome后期版本和现在的大多数浏览器则使用Blink内核,Firefox使用Gecko内核。这导致了...

    High Performance JavaScript(高性能JavaScript)读书笔记分析

    第五章:字符串和正则表达式 字符串操作和正则表达式是JavaScript中常见的操作,但也是潜在的性能瓶颈所在。回溯是正则表达式匹配中一个常见但可能导致效率低下的问题。 第六章:快速响应的用户界面 在Web应用中,...

    python入门到高级全栈工程师培训 第3期 附课件代码

    第5章 01 上节课复习 02 文件合并与文件归档 03 文件归档与两种压缩方式 04 vim编辑器 05 系统启动流程 06 grub加密 07 bios加密 08 top命令 09 free命令 10 进程管理 第6章 01 上节课复习 02 磁盘分区 03 文件...

    javascript讲义(1).pptx

    #### 五、JavaScript特性 - **解释性语言**:无需编译成文件,直接由浏览器解释执行。 - **跨平台**:能在多种操作系统和设备上运行。 - **单线程**:JavaScript的主要执行模型是单线程的。 - **ECMA标准**:为了...

    JS数独 v1.0.2

    《JS数独 v1.0.2》是一款基于JavaScript实现的数独小游戏,适用于现代浏览器,尤其是基于WebKit内核的浏览器如Chrome或Safari。在IE浏览器中,部分验证功能可能无法正常工作,但不影响基本的游戏体验。这个项目展示...

    fsdfsdfdsf

    5. **XML验证器设计** (第 5 章): 讨论了如何设计XML验证器,从最初的简单实现到逐步优化,包括复杂度分析和性能提升。 6. **集成测试框架** (第 6 章): 关注于构建灵活、易用的自动化测试框架,以及在设计时考虑的...

    代码之美(中文完整版).pdf

    第5章 正确、优美、迅速(按重要性排序):从设计XML验证器中学到的经验 5.1 XML验证器的作用 5.2 问题所在 5.3 版本1:简单的实现 5.4 版本2:模拟BNF语法——复杂度O(N) 5.5 版本3:第一个复杂度O(log N)的优化 5.6 ...

    JsInWinform(在winform中调用JS代码)

    - **`InvokeScript`方法**:调用`webBrowser1.Document.InvokeScript`方法,传入JavaScript函数名和参数数组,即可执行JavaScript函数。 4. **从JavaScript调用.NET**: - **设置`ObjectForScripting`**:为`...

    最新史上最全前端面试题(含答案).docx

    20. **数组方法**:pop()删除并返回数组最后一个元素,push()在数组末尾添加元素,unshift()在数组开头添加元素,shift()删除并返回数组第一个元素。 以上内容涵盖了前端开发中的基础理论、HTML结构、CSS样式、...

    ActionScript开发技术大全

    第5章ActionScript3.0中的String对象 104 5.1创建String对象 104 5.2字符串处理 105 5.2.1字符处理 105 5.2.2字符串比较 107 5.2.3裁割与连接 108 5.2.4查找、匹配与替换 110 5.2.5提取子串 112 5.2.6大小写转换 113...

    2016前端面试题及答案.docx

    19. **数组方法**:pop()移除并返回数组最后一个元素,push()在末尾添加元素,unshift()在开头添加元素,shift()移除并返回数组第一个元素。 以上是2016年前端面试中的部分关键知识点,这些内容至今仍对前端开发者...

    【web前端开发面试题及答案】前端开发面试题及答案.docx

    18. **数组方法**:pop()移除并返回数组最后一个元素,push()在末尾添加元素,unshift()在开头添加元素,shift()移除并返回数组第一个元素。 19. **事件绑定**:包括传统的事件处理程序(如onclick)和DOM2级事件...

    前端面试题

    - `shift()`:从数组开头移除第一个元素。 #### 十六、事件绑定与事件流的区别 - **事件绑定**:将事件处理程序与特定的DOM元素关联起来。 - **事件流**:描述事件在DOM树中的传播过程。 - **IE与DOM事件流的区别...

    ES6最简单的构建环境没有之一

    在现代前端开发中,ES6(ECMAScript 2015)已经成为主流的JavaScript语法,它引入了一系列新的特性,极大地提升了代码的可读性和可维护性。要搭建一个ES6的学习环境,我们可以遵循以下几个简单步骤。 1. **浏览器...

    malevich:使用粒子系统复制马列维奇至上主义,第18个建筑构图

    《使用粒子系统复制马列维奇至上主义:JavaScript实现解析》 ...通过JavaScript编程,我们不仅能理解至上主义的精神内核,还能感受到数字艺术的魅力,这正是现代技术赋予我们重新解读和创作经典的可能性。

    jquery学习笔记

    7. **扩展JavaScript内核**:jQuery还提供了对JavaScript语言本身的增强,包括数组操作等功能,这使得开发者可以更加高效地处理数据。 #### 三、jQuery项目组成 - **jQuery Core (核心库)**:这是jQuery的基础,...

    java web面试题目

    #### 五、JavaScript消除数组中的重复元素 消除数组中重复元素的一种简单方法是使用ES6的`Set`数据结构。 **示例代码:** ```javascript const arr = [1, 2, 3, 4, 5, 5, 6, 6, 7, 8, 9, 9]; const uniqueArr = ...

Global site tag (gtag.js) - Google Analytics