javascript中length属性的探索
JavaScript属性 探索 length
2023-06-13 09:14:29 时间
例子1:
复制代码代码如下:
varobj={0:"a",1:"b"}
alert(obj.length);//undefined
vararr=["a","b"]
alert(arr.length);//2
从上面的例子看,类数组对象中的length属性并不和它储存的数据数量直接挂钩,无论是索引属性(0,1)还是length属性都作为对象的普通属性存在,它们之间并没有任何关系,js引擎并不会根据储存数据的数量来自动计算类数组对象的长度。
但是类数组对象的length所确实和存储的数据量没有任何关系么?例子2说明并非如此:
例子2:
functionmyarr(){}
varm=newmyarr();
Array.prototype.push.apply(m,["cson","lai","xiaoc"]);
alert(m.length);//IE8以下:undefined其他浏览器:3
alert(m[2]);//IE8以下:undefined其他浏览器:‘xiaoc"
从例子2可以看到,除了IE8以下版本,在通过强制使用数组方法为类数组对象添加元素时,对象的length属性也会被计算。而IE8以下版本貌似不支持强制使用数组方法为类数组对象添加元素。
例子3:
该例子在例子2的myarr构造函数中添加一个初始化操作,在类数组对象初始化时添加一个元素,怪异的事情发生了:
functionmyarr(){this[0]="cc";}
varm=newmyarr();
Array.prototype.push.apply(m,["cson","lai","xiaoc"]);
alert(m.length);//ie8以下:undefined其他:3
alert(m[2]);//ie8以下:undefined其他:xiaoc
ie8以下版本浏览器继续貌似不支持强制使用数组方法,这个再下一个例子中会作讨论。而对于其他浏览器,length属性输出为3,而索引为2的元素是"xiaoc‘,显然js引擎完全忽略了类数组对象原来所存在的索引为0的元素‘cc"!马上我们再看下一个例子,这个例子在例子3的基础上多加一个对length属性的初始化:
functionmyarr(){this[0]="cc";this.length=1;}//多加一个length的初始化
varm=newmyarr();
Array.prototype.push.apply(m,["cson","lai","xiaoc"]);
alert(m.length);//输出4
alert(m[2]);//输出"lai‘
奇怪的事再次发生,这次所有浏览器(包括ie67)都正确输出4,索引为2的元素正确输出为"lai‘,可见IE67添加了length属性的初始化之后,可以正常使用数组方法了。
现在再试试把length属性初始化为不合法类型:
例子4:
functionmyarr(){this[0]="cc";this.length="bo";}//length设置为不能转换为number的不合法类型
varm=newmyarr();
Array.prototype.push.apply(m,["cson","lai","xiaoc"]);
alert(m.length);//输出3
alert(m[2]);//输出"xiaoc‘
functionmyarr(){this[0]="cc";this.length="1";}//length设置为能转换为数字的不合法类型
Array.prototype.push.apply(m,["cson","lai","xiaoc"]);
alert(m.length);//输出4
alert(m[2]);//输出"lai‘
从上面的所有例子来看,我们可以作出一个推断,在使用数组方法时(这里以push为例),大概是这样的流程:
IE67:
可见IE67并非不支强制持使用数组方法添加元素,但是会先判断length属性是否存在,如果不存在,则返回,不做任何操作。如果length属性为不合法值,则尝试转换为number类型,如果转换失败则length设置为0,这就可以解析例子2,3里输出的undefined和例子4的正确输出。
其他浏览器:
其他浏览器会根据length属性作不同操作,如果length属性不存在,则设置length为0,如果length属性为不合法值,则尝试转换为number类型,如果转换失败则也length设置为0。
正因为length属性对于数组方法有如此决定性的作用,因此js引擎禁止了对length属性写入不合法值:
vararr=["1","2","3"];
arr.length="undefined";//报错invalidarraylength
从上面的例子中,我们可以得出一个结论:当我们使用类数组对象时,为了避各种length计算不正确引起的怪异问题,我们应该在初始化类数组对象时初始化length属性的值,如果在初始化时添加了元素但却没有设置length属性的值,在使用数组方法时,IE67会忽略所有操作,其他浏览器则会忽略初始化时添加的元素。
另外再介绍length属性带来的另一个问题:
请看例子5:
functionmyarr(){}
myarr.prototype=newArray();
varm=newmyarr();
m.push("cson","lai","xiaoc");
alert(m.length);//IE67:0其他:3
alert(m[2]);//所有浏览器:"xiaoc‘
当使用原型继承数组时,IE67下length会始终为0,无论你有多少个元素,其他浏览器则正常。
即使强制设置length属性,IE67下死活为0:
functionmyarr(){}
myarr.prototype=newArray();
varm=newmyarr();
m.length=10;
alert(m.length);//IE67:0其他:10
因此得出结论:IE67下对象原型继承数组时length属性会一直为0,因此如果类数组对象需要使用数组的方法,不要去继承数组,而应该使用Array.prototype.xxx.apply(obj,[]);的方法,并且记得正确初始化length属性的值。
相关文章
- javascript 基础_JavaScript高级编程
- html5 scrollheight,JavaScript之scrollTop、scrollHeight、offsetTop、offsetHeight等属性学习笔记…[通俗易懂]
- 【说站】javascript构造函数如何借用
- JavaScript 数组常用属性和方法(上)
- javascript获取当前是http还是https
- javascript对象的定义方法
- JavaScript节点操作以及DOMDocument属性和方法
- javascript火狐(firefox)不显示本地图片问题解决
- JavaScript入门教程(4)js浏览器对象
- 原生javascript获取元素样式属性值的方法
- JavaScript常用对象的方法和属性小结
- javascript学习笔记(二十)获得和设置元素的特性(属性)
- 常用一些Javascript判断函数
- JavaScript高级程序设计阅读笔记(十六)javascript检测浏览器和操作系统-detect.js
- 探讨javascript是不是面向对象的语言
- 如何通过javascript操作web控件的自定义属性
- 利用noesis.Javascript开源组件.Net中执行javascript脚本
- javascript和jquery修改a标签的href属性
- javascript操作css属性
- JavaScript类属性的访问方式详解
- JavaScript运行时库属性一览表
- JavaScript控制各种浏览器全屏模式的方法、属性和事件介绍
- Javascript中对象继承的实现小例
- JavaScript极简入门教程(三):数组
- javascript数组操作方法小结和3个属性详细介绍