JavaScript基本数据类型之对象-学习笔记

本文思维导图

1 基本概念及语法

对象(Object)是JavaScript最重要的数据类型。

简单地说,对象就是一组“键值对”的集合,而且它是一个无序复合数据集合

1.1 基本语法

如下代码所示:大括号就定义了一个对象,并被赋值给一个变量obj。该对象内部有两个键值对(或叫成员),键和值之间用冒号分隔,两个键值对之间用逗号分隔。

注:最后一个键值对后面加不加逗号都可以,建议省略。

var obj={
    foo:'Hello',
    bar:'World'
}

上述obj对象的键名默认都是字符串(ES6中的Symbol类型也可以用作键名),即便为数值,也会被自动转为字符串,因此加不加引号都可以。

注:若键名不符合标识符的命名条件,则必须加上引号才可以,否则会报错。

1.2 对象的属性

键名又被称为属性,而其对应的键值可以是任意数据类型;若键值(即属性的值)为函数,则该属性又被称作方法,它可以像函数那样调用。

var obj={
    p:function(x){
        return 2*x;
    }
}

obj.p(1);//结果为2

1.3 链式引用

若键值(即属性的值)为一个对象,就形成了链式引用

如下例子:o1的属性foo指向对象o2,这样就可以链式引用o2的属性。

var o1={};
var o2={bar:'hello'};
o1.foo=o2;

o1.foo.bar //输出为“hello”

上述例子中o1的属性并没有在声明时就指定,因为属性可以被动态创建

2 对象的引用

如果多个不同的变量名指向同一个对象,那么这些变量名则指向相同的内存地址,当修改其中一个变量时,会影响到其他所有变量。

var o1={};
var o2=o1;

o1.a=1;
o2.a //值也为1

o2.b=2;
o1.b //值同样为2

若取消某一个变量对于原对象的引用,则不会影响到其他的变量。

var o1={};
var o2=o1;

o1=1; //给o1赋新值则可取消o1对原对象的引用
o2 //此时o2仍指向原来的对象{}

上述的引用只局限于对象,若两个变量指向同一个原始类型的值,那么变量都是值的拷贝

如下代码:当x的值发生变化,y值并没有改变,这表明xy并没有指向同一个内存地址。

var x=1;
y=x;

x=2;
y //此时y值仍为1

3 属性的操作

3.1 属性的读取

方法1:使用点运算符:语法为:对象.属性,例如obj.prop

方法2:使用方括号运算符:语法为对象.['属性'],例如obj['prop']

举例:

  1. 若使用方括号运算符,属性名(或键名)需要放在引号中,否则会被看作变量来处理。

    var foo = 'bar';
    var obj = {
      foo: 1,
      bar: 2
    };
    
    obj.foo  // 1
    obj[foo]  // obj[foo]即为obj['bar'],结果显然为2
    
  2. 方括号内部可以使用表达式(仍是上面的例子):

    obj['b'+'a'+'r'] //即obj['bar'],值显然为2
    
  3. 若属性为数字,则在读取时可以不加引号,因为它会被自动转为字符串,但此时需要用方括号取值。若此时用点运算符则会报错,因为点运算符会被认为是小数点。

    var obj={
        123:'hello world'
    };
    
    obj.123 //报错
    obj[123] //相当于obj['123'],正确,输出值为“hello world”
    

3.2 属性的赋值

属性的赋值方法和第一小节的读取方法一样,也是使用点运算符方括号运算符。例如:

var obj={};
obj.foo='hello';
obj['bar']='world';

3.3 属性的查看

查看一个对象本身所有属性,可以使用Object.keys()方法,例如:

var obj={
    key1:1,
    key2:2
}

Object.keys(obj); //输出结果为["key1", "key2"]

3.4 属性的删除

delete命令用于删除对象的属性,删除成功后返回true

具体测试如下:
在这里插入图片描述
从上面的测试也容易看出:由于删除一个不存在的属性仍返回true,因此不能根据delete命令的结果,来判断某个属性是存在的

那么什么时候delete命令会返回false呢?

答案是只有一种情况:若将对象的configurable属性设置为false,即不可配置,此时该属性将无法删除,delete命令此时会返回false。具体请参考:Object.defineProperty() | MDN (mozilla.org),这里不再赘述。

3.5 判断属性是否存在

3.5.1 in运算符

in运算符用于检查对象是否包含某个属性(检查的是键名而非键值),若包含则返回true,否则返回false。语法为:字符串 in 对象

3.5.2 hasOwnProperty()方法

在JavaScript中,像toString属性每个对象都会有(因为这个属性是继承来的),因此在使用in运算符判断都会返回true,这时,可以借助hasOwnProperty()方法来判断是否为对象自身的属性。

var obj={};
if('toString' in obj){
    console.log(obj.hasOwnProperty('toString')) //显然输出为:false
}

3.6 属性的遍历

for...in循环用来遍历一个对象的全部属性

举个例子好理解:

var obj={a:1,b:2,c:3};

for (var i in obj){
    console.log('键名:',i);
    console.log('键值:',obj[i]);
}

输出结果为:

键名: a
键值: 1
键名: b
键值: 2
键名: c
键值: 3

for...in循环输出的项需满足以下两个条件:

  1. 它遍历的是对象所有可遍历(enumerable)的属性会跳过不可遍历的属性
  2. 它不仅遍历自身的属性,还遍历继承的属性

问题来了:那为何上述例子没有输出继承属性toString呢?
那是因为该属性默认是不可遍历的,由于不满足上面的第一个条件,因此没有被输出。

技巧:在使用for...in循环时可以结合hasOwnProperty()方法,首先在循环内部判断该属性是否为自有属性。

4 with语句

with语句可以更方便地操作同一个对象的多个属性。语法如下:

with(对象){
    语句;
}

例1:我们可以利用with语句一次为对象修改多个属性:

var obj={p1:1,p2:2};
with(obj){
    p1=4;
    p2=5;
}

上面等同于obj.p1=4;obj.p2=5;

例2:可以同时读取对象的多个属性:

with(document.links[0]){
    console.log(href);
    console.log(title);
    console.log(style);
}

等同如下代码:

console.log(document,links[0].href);
console.log(document,links[0].title);
console.log(document,links[0].style);

需要注意的是:with区块内部有变量的赋值操作,必须是当前对象已经存在的属性,否则会创建一个当前作用域的全局变量。如下测试所示:由于对象被创建时没有p1属性,因此输出obj.p1时会返回undefined,对p1p2赋值等于创造了2个全局变量p1p2

在这里插入图片描述
综上来看,with语句会造成绑定对象不明确的问题,因此非必须情况下尽量避免使用with语句。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值