前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >JavaScript对象length

JavaScript对象length

作者头像
晚晴幽草轩轩主
发布于 2018-03-27 08:23:24
发布于 2018-03-27 08:23:24
2.6K00
代码可运行
举报
文章被收录于专栏:静晴轩静晴轩
运行总次数:0
代码可运行
前几日有在Javascript数组操作一文中稍提及了数组的length属性;深入一点探究,就发现JS这length确有许多难为所知的特性。这就边学边探究下这朵奇葩属性;这里边深入边记载。

可变的数组length属性

和其他大多数语言不同的是,JavaScript数组的length属性是可变的,这一点需要特别注意。当length属性被设置得更大时,整个数组的状态事实上不会发生变化,仅仅是length属性变大;当length属性被设置得比原来小时,则原先数组中索引大于或等于length的元素的值全部被丢失。下面是演示改变length属性的例子:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var arr=[12,23,5,3,25,98,76,54,56,76];
console.log(arr.length);  // 10

arr.length=5; //将数组的长度减少到5,索引等于或超过5的元素被丢弃
alert(arr[8]); //显示第9个元素已经变为"undefined"

arr.length=10; //将数组长度恢复为10
alert(arr[8]); //虽然长度被恢复为10,但第9个元素却无法收回,显示"undefined"

arr[15] = 34;
console.log(arr.length);  //16

console.log(arr[10]);     //undefine
console.log(arr.toString())
//12,23,5,3,25,98,76,54,56,76,,,,,,34

length对象不仅可以显式的设置,它也有可能被隐式修改。JavaScript中可以使用一个未声明过的变量,同样,也可以使用一个未定义的数组元素(指索引超过或等于length的元素),这时,length属性的值将被设置为所使用元素索引的值加1。例如下面的代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var arr=[12,23,5,3,25,98,76,54,56,76];
console.log(arr.length);  // 10

arr[15] = 34;
console.log(arr.length);  //16

console.log(arr[10]);     //undefine
console.log(arr.toString())
//12,23,5,3,25,98,76,54,56,76,,,,,,34

JS对象的length

在JS中来判断一个对象是否为数组,是需要费点周折的。但以是否具有length属性来衡量之,显然是不合理的。length数组不是独有的,JS对象也是可以用的(当然,数组也是对象的一种~数组对象)。譬如:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var obj = {'1':'gg', '2':'love', '4':'meimei', length:5};
console.log(obj.length); // 5

JavaScript中有一些看起来像却又不是数组的对象,唤作: 类数组。一个类数组对象:

  • 具有:指向对象元素的数字索引下标以及length属性告诉我们对象的元素个数
  • 不具有:诸如 push forEach 以及 indexOf 等数组对象具有的方法

两个典型的类数组的例子是:DOM方法 document.getElementsByClassName()的返回结果(实际上许多DOM方法的返回值都是类数组)以及特殊变量 arguments [1]。例如你可以通过以下方法确定函数参数的个数:arguments.length 你也可以获取单个参数值,例如 arguments[0]。 如果这些对象想使用数组的方法,就必须要用某种方式“借用”。这里的“借用”可以借助JS的call,apply方法来实现。有时候处理类数组对象的最好方法是将其转化为数组。 这项工作也可以使用通用方法来完成:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var obj = {'1':'gg','2':'love','4':'meimei',length:5};
Array.prototype.join.call(obj , '+'); //'+gg+love++meimei'

类数组判断

聊起JS对象的length就有必要说下这个类数组判断。之前有在IOS 8 Safari JIT bug影响jQuery和underscore记录使用Underscore在IOS机器引起的问题。而对于此问题,jQuery,Underscore方面修复的办法就是改变了类数组判断的判断方式:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
//underscore 1.7.0 _.each部分代码
var i, length = obj.length;
if (length === +length) {
    ......
}

对比与underscore1.8.3 _.each部分代码(是采用isArrayLike来判断的):

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var MAX_ARRAY_INDEX = Math.pow(2, 53) - 1;
var getLength = property('length');
var isArrayLike = function(collection) {
  var length = getLength(collection);
  return typeof length == 'number' && length >= 0 && length <= MAX_ARRAY_INDEX;
};

var property = function(key){
  return function(obj){
    return obj == null ? void 0 : obj[key];
  }
}

对于数组是有下标的,其下标的范围是”大于等于0并小于2^32-1的整数”,如果数字太大的话你想难为JavaScript是做不到的。因为其会自动将其转化为”字符串”。而underscore1.8.3用的MaxLength是Math.pow(2, 53) - 1(其值:9007199254740992),不解?,待探究下~

而《javascript权威指南》上给出的代码用来判断一个对象是否属于“类数组”。其code如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
function isArrayLike(o) {
    if (o &&                                // o is not null, undefined, etc.
        typeof o === 'object' &&            // o is an object
        isFinite(o.length) &&               // o.length is a finite number
        o.length >= 0 &&                    // o.length is non-negative
        o.length===Math.floor(o.length) &&  // o.length is an integer
        o.length < 4294967296)              // o.length < 2^32
        return true;                        // Then o is array-like
    else
        return false;                       // Otherwise it is not
}

##数组的存储 在JavaScript中数组元素存储是稀疏的,这也就意味着数组的下标不会落在一个连续的数字范围由,只有那些真正存储在数组中的元素才能够分配到内存,其余均不会浪费你宝贵的内存空间。比如如下代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var arr = new Array();   //声明一个空数组
arr[0] = 'jeff';
arr[1000] = 'jade';
console.log(arr.length); //1001 嗯。从0到1000
console.log(arr[999]);   //undefined 没有定义

在JavaScript中数组元素本身,可以是各种类型Null,function,string,object对象等都可以。这一点毋庸置疑;但前两日在学习数组reduce方法的时候,竟然被涨了姿势了,代码走起:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var arr = ["apple","orange",'pear','jade'];
var arrJade;
function passValue(){
    return arr.reduce(function(prev,next){
        console.log("prev---:",prev);
        console.log("next---:",next);

        prev[next] = 1;
        //console.info('prev type:'+ typeof(prev)); // [object Array]
        console.log(Object.prototype.toString.call(prev));
        arrJade = prev;
        return prev;
    }, []);    
}
console.log("reduce With [] as an additional parameter:",passValue());
//reduce With [] as an additional parameter: [ apple: 1, orange: 1, pear: 1, jade: 1 ]
console.log(arrJade.length); // 0
arrJade.push('jade');    
console.log(arrJade);        // [ 'jade', apple: 1, orange: 1, pear: 1, jade: 1 ]
console.log(arrJade.apple);  // 1

这里可以看出,可以得到一个类Object对象的数组:只是被包裹的是[],而非{};且此时该“数组”是有length属性的,只不过length是0而已。这个“数组”,以console.log(Object.prototype.toString.call(arrJade));来判别是数组无疑。但是倘若类同如此这样直接定义一个“数组”,却是断然不可以的,请看如下代码:。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var arr = [apple: 1, orange: 1]; //这么搞,编译都过不了,语法错误❌
//Uncaught SyntaxError: Unexpected token : ...

//but,可以像使用reduce方法一样,可以构造出这样的数组!
var arrTest = [];
arrTest["apple"] = 1;
arrTest["orange"] = 1;
console.log(arrTest);       //[apple: 1, orange: 1]
console.log(arrTest.length) // 0
arrTest.push('pear');
console.log(arrTest);       // ["pear", apple: 1, orange: 1]
console.log(arrTest.length) // 1

console.log(arrTest.apple); //1   arrTest['apple']当然也可以访问。

arrTest["pear"] = 1;
console.log(arrTest);       //["pear", apple: 1, orange: 1, pear: 1]

既然这是一个数组,但为何不能直接如此构造,这一点现在还没搞搞明白,呜呜~。而这样:arrTest[“apple”] = 1; 操纵一个数组,无形的将该项元素对象化了,又没用{}将其包裹,致使其“游离”于此数组一级对象一列,数组能够直接访问。但是,又不在length计数范围。length的数组下表是有对应关系的,当然这里也不能使用数组带下标来访问了。

JS数组,对于诸如Number,String之类的类型数据会被直接压入栈中,而引用类型只会压入对该值的一个索引(即C中所说的保存了数据的指针)。这些数据时储存在堆中的某块区间中,堆栈并不是独立的,栈中也可以在堆中存放。那么那些直接游离在数组中的Object元素项,存储地是在哪儿呢?额额,还是没搞搞明白,!?(・_・;?。

对于JS,尚有诸多未知,待学待探究,即便是这随便一个属性:length!!!

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2015-10-08,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
在Windows Mobile上使用WINCE自带数据库
    通过数据库,可以方便地存储和检索数据,极大地提高工作效率。在Windows CE .NET 4.2上,自带了一个数据库,具体我们可以参考MSDN上的网页:Microsoft Windows CE .NET 4.2 Database Reference。由于它最多只支持4种排序索引,这种数据库适合存储的数据量较小、数据结构相对简单的情况。它支持的数据类型包括2/4字节有/无符号整数、日期时间、Unicode字符串、CEBLOB、布尔和8字节有符号值。 数据库的主要操作包括以下几个方面: 装配数据库
ShiJiong
2018/01/11
1.7K0
在Windows Mobile上使用WINCE自带数据库
“零基础”学习WinCE开发
      Windows CE 是微软公司开发的一个针对小型设备(它是典型的拥有有限内存的无磁盘系统)的通用操作系统。主要用于嵌入式系统和移动终端设备上,操作界面和PC机上的WinXp系统比较类似,例如也是窗口化的操作界面,也具有磁盘资源管理器,文件系统和网络通讯协议和WinXp一样,程序开发也和WinXp环境下的程序开发。具体关于WinCE的介绍可以到网上搜索相关资料。个人的理解就是,WinCE可以看作一个精简后的WinXp系统,“麻雀虽小,五脏俱全”,在一些小型工控系统中可以发挥巨大的作用。
用户1170933
2022/05/10
1.5K0
“零基础”学习WinCE开发
Navi.Soft31.WinCE框架.开发手册(含下载地址)
1.概述 1.1应用场景 随着物联网的普及,越来越多的制造商对货品从原料配备,加工生产,销售出库等环节的要求和把控越来越高.在此情况之下,传统的ERP软件已经无法满足现有的操作流程. 移动设备的应用,在很大程度上弥补了传统ERP软件的不足,在物联网中,也起着非常重要的角色. 移动设备目前包括微软WinCE系统,谷歌的Android系统和苹果的IOS系统.Android和IOS系统目前在个人消费领域应用非常广泛,但在应用软件领域目前使用不多.WinCE系统出道较早,也属于名门之后.在此系统中开发的应用软件也很
用户1219352
2018/02/01
1.5K0
Navi.Soft31.WinCE框架.开发手册(含下载地址)
Battery Status on Windows Mobile
    大家知道,我们可以通过Start->Settings->Systems->Power来查看系统的电池情况,包括电池的类型,剩余的电量等等,如下图1所示: 图1:Windows Mobile自带
ShiJiong
2018/01/11
7910
Battery Status on Windows Mobile
在Windows Mobile上实现自动拼写和匹配建议
使用Windows Mobile手机的朋友,应该有一个体会,那就是要查找某个联系人,在输入目标联系人名字的过程中,系统会实时按照所输入的内容来筛选,呈现在列表中,供用户选择。同样,如果我们要直接拨打电话,在输入电话号码的过程中,系统也会实时地将输入的号码和联系人库进行比较,将匹配的联系人显示在列表中,供用户选择。     大家不要小看了这一个功能,其实,在设备小巧、需要花费大力气来处理输入和输出的嵌入式设备上,用户对UI的体验是至关重要的。在我看来,这个自动拼写建议是非常有用的,至少目前很多软件(诸
ShiJiong
2018/01/11
7900
在Windows Mobile上实现自动拼写和匹配建议
Windows Mobile Jump Start Guide
这篇文章是交给MSTC的作业,发上来和大家共享,希望对入门windows mobile平台开发的朋友有帮助。 1. Windows Mobile简介 Windows Mobile™ 是基于 Micro
ShiJiong
2018/01/10
1.5K0
Windows Mobile Jump Start Guide
Alpha Blending and Alpha Channel on Windows Mobile
      2007年的时候,Alex在《Compelling UI's in NetCF anybody?》一文中,讲述了windows mobile 5平台上如何利用AlphaBlend做很酷的透
ShiJiong
2018/01/11
1.1K0
Alpha Blending and Alpha Channel on Windows Mobile
Windows Mobile上的无线网络接入点扫描
  不用我多说,相信大家对于Wifi在手机上的重要性都有所认识。大家都希望能够在小巧的移动设备上实现高速移动互联网,和桌面PC的差距越小越好。   上个月,通信世界网抛出了一个“中国电信CDMA+Wi-Fi战略分析”的消息,称中国电信将在未来三年陆续投资800亿元资金用于升级、改造、优化CDMA网络,并采用CDMA + WLAN的组合方式,充分发挥CDMA与WLAN的组合优势,提供无缝的移动无线宽带上网服务,帮助中国电信迅速打开移动宽带市场。中国电信在南方21省做了大量Wi-Fi部署,计划到年底完成2.5万
ShiJiong
2018/01/11
9680
Windows Mobile上的无线网络接入点扫描
ZigBee On Windows Mobile--2.硬件和软件设计
    继续上一篇”ZigBee On Windows Mobile--1.背景和结构”,今天来讲讲硬件和软件设计。硬件设计主要是做ZigBee模块,输出文件一般包括原理图和PCB图。PCB图是最终给制板厂商的文件,制板厂商将PCB文件转化为Gerb文件进行PCB板加工。软件设计包括两部分,即ZigBee模块中的嵌入式程序和Windows Mobile端的应用程序,这两个软件模块运行在不同的平台之上,硬件上通过UART口进行通信。     硬件设计使用了比较传统的Protel99se,采用了MC1319
ShiJiong
2018/01/11
8410
ZigBee On Windows Mobile--2.硬件和软件设计
java通过jdbc连接SQL数据库(SQL2012举例)
首先,在连接数据库之前必须保证SQL Server 2012是采用SQL Server身份验证方式而不是windows身份验证方式。如果在安装时选用了后者,则重新设置如下:
Lcry
2022/11/29
1.6K0
使用Windows Embedded Source Tools for Bluetooth Technology简化蓝牙开发
“Windows Mobile上的蓝牙点对点通信”介绍如何在两台Windows Mobile设备上建立点对点的蓝牙通信,继续这个话题,WM6的SDK中,给出了另外一个蓝牙通信的例子,那就是SpaceWar2D。SpaceWar2D使用了Windows Embedded Source Tools for Bluetooth Technology来做蓝牙通信,在两台WM设备间建立连接,然后进行简单的游戏。       Windows Embedded Source Tools for Bluetooth Te
ShiJiong
2018/01/11
9040
使用Windows Embedded Source Tools for Bluetooth Technology简化蓝牙开发
IM over Socket Between Windows Mobile Devices
    在《利用WiFi在Windows Mobile上建立Ad-hoc网络》一文中,讲述了利用WiFi在Windows Mobile上建立Ad-hoc网络的方法,在Windows Mobile 6与Windows Mobile 2003se for Pocket PC给出了演示。那么,点对点的Ad-hoc网络能够完成什么功能呢?一方面,它可以用来消息的实时发送与接收,也就是俗称IM(Instant Messager);另一方面,可以用来传送文件。这篇文章先来讲讲如何利用Socket来实现Windows M
ShiJiong
2018/01/10
7890
IM over Socket Between Windows Mobile Devices
美化Windows Mobile上的自定义数据表
    前段时间做实验室项目,需要以报表的形式将数据展示给用户。首先想到的是visual studio自带的listview,用起来是比较方便,可是看着不美观,说白了,就是吸引力不够。于是,我想到了使用Alpha Blend来做一个半透明效果的表格。因为在今年2月份的时候,Alex Yakhnin做了一次名为《24 Hours of Windows Mobile Application Development: Creating Compelling and Attractive UIs for Windo
ShiJiong
2018/01/10
1.1K0
美化Windows Mobile上的自定义数据表
Endnote for Windows Mobile
  想必园子里有好多朋友都写过paper吧,在阅读文献的时候,是不是觉得管理文献这个事情很麻烦。我正处于刚刚起步的阶段,英语写译老师Greatlion给我们推荐了一款文献管理工具Endnote,在学校FTP上下载了Endnote X2.0.1。安装了以后,发现Endnote还提供了移动设备上的程序,特别是Windows mobile和Palm的版本。于是乎心里大喜,以后在我WM手机上又多了一项功能--参考文献学习。虽然在WM上看pdf格式的paper有点鸡肋,但是浏览Abstract之类的功能还是不错的,至
ShiJiong
2018/01/11
8740
Endnote for Windows Mobile
Qt配置使用VS2010进行开发
它包括跨平台类库、集成开发工具和跨平台 IDE。使用 Qt 您只需一次性开发应用程序,无须重新编写源代码,便可跨不同桌面和嵌入式操作系统部署这些应用程序。
阳光岛主
2019/02/19
1.7K0
pycharm中安装django_pycharm环境配置教程
原文转载自:http://www.cnblogs.com/hwtmhj/p/6746151.html
全栈程序员站长
2022/09/27
3.9K0
pycharm中安装django_pycharm环境配置教程
管理SQL Server 2008 数据库角色
角色是SQL Server 2008用来集中管理数据库或者服务器的权限。数据库管理员将操作数据库的权限赋予角色。然后,数据库管理员再将角色赋给数据库用户或者登录账户,从而使数据库用户或者登录账户拥有了相应的权限。 
幽鸿
2020/04/02
2.3K0
管理SQL Server 2008 数据库角色
人人网 Windows Phone 7 应用开发起步
        目前,人人网在国内高校学生中的普及率非常高。前段时间,大概是11月下旬的样子,人人网发布了Windows Phone 7客户端的公测版。我想,Windows Phone 7本地化的优劣,直接关系到其将来在国内的市场份额。而诸如人人等针对学生群体的SNS应用,也将影响到高校学生对WP7平台的认可程度。人人的WP7公测版大家可以去网站上下载,如果没有WP7设备,也可以通过SDK中的Application Deployment工具部署到模拟器上进行试用。这里给出WP7平台开发人人应用的相关流程。
ShiJiong
2018/01/10
6570
人人网 Windows Phone 7 应用开发起步
Java编程技术教程之Java开发入门
Java经过了多年的快速发展,成为了最受欢迎的开发语言之一,截至目前有超过400万以上的程序员在使用Java语言,现在的Java是第9个主要版本。
张哥编程
2024/12/19
2210
Java编程技术教程之Java开发入门
sql数据库打包部署安装
目的:在客户端服务器上”附加数据库文件”。 一).创建部署项目 1. 打开VS.NET2005。 2.在“文件”菜单上指向“新建项目”。 3. 在“新建项目”对话框中,选择“项目类型”窗格中的”其他项
阿新
2018/04/09
2.5K0
sql数据库打包部署安装
推荐阅读
相关推荐
在Windows Mobile上使用WINCE自带数据库
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验