这次的分享,主要还是想跟大家聊聊Javascript语言中很重要的概念之一,对象。为什么说之一呢?因为Javascript其他重要概念还包括:作用域 作用域链 继承 闭包 函数 继承 数组 ...... 有机会会跟大家分享这些概念的。
以下的介绍会分为如下:
1:前言
2:概述
2.1:对象创建
2.2:对象键名与键值
2.3:对象属性
2.4:对象引用
3:对象属性
3.1:读取属性
3.2:属性赋值
3.3:查看所有属性
3.4:删除属性
3.5:遍历属性
1:前言
Javascript拥有七种数据类型,其中分为两类。原始数据和复杂数据类型。原始数据类型:包括 字符串,数组,数字,布尔值,Null,Undefined。复杂数据类型:包括 对象。
对象是Javascript的核心概念,也是最重要的数据类型。Javascript所有数据都可以视为对象。都可以使用内置的方法。但是除了两个例外,就是Null和Undefined。
代码如下:
1 [1,2,3].toString() // "1,2,3"
2 "ha".toString() // "ha" 3 false.toString() // ‘false‘
一个对象就是一系列属性的集合,一个属性包含一个名字和一个值。一个属性也可以是函数,这种情况下这个属性被称为方法,可以拿汽车来做一个形象化的对比。
汽车是一个对象,拥有属性颜色,重量,车型,方法便是可以开上马路了。
写在代码中,就是:
1 var car = {
2 "color": "red",
3 "weight": "1.4吨", 4 "module": "SUV" 5 "use": function() { 6 return "drive"; 7 } 8 };
2:概述
2.1:对象创建
1 var o = {
2 "p": "Hello World",
3 "name": "Keith Chou" 4 };
上面的代码中,大括号就定义了一个对象,它被赋值给全局变量o。这个对象(对象的名字随便定义)内部包含一个键值对,p是键名,字符串Hello World是键值。键名和键值用":"分离,不同键值对之前通过","分离,最后一个键值可不用逗号。但是我建议最后都不要加上。右花括号" } "后边要加上分号";"。
对象创建有三种方法:
1 var o1 = {};
2 var o2 = new Object(); 3 var o3 = Object.crete(null);
上面三行语句都是等价的。第一种使用花括号来创建一个对象,这是最简便的方法。第二种采用构造函数的写法清晰的表明了意图。第三种写法多用于对象继承的场合。
2.2 键名与键值
1 var o = {?
2 "say": "Hello World",
3 ?"name": "Keith Chou", 4 ?"height": "180", 5 ?"age": 21 6 };
以上用第一种方法创建对象,并赋值给全局变量o。键名即如下值:"say","name","height","weight"。键值即如下值:"Hello World","Keith Chou" ...
对象的所有键名都是字符串,加不加双引号都可以。对象的键值如果是英文,则必须加引号,否则会当成变量处理。如果是数字,加了引号则当成字符串处理,不加引号当成数字类型处理。
1 var o = {?
2 o1: 180,
3 ?o2: "180" 4 }; 5 o.o1 // 180,数字类型 6 o.o2 // "180" ,字符串类型
注意,Javascript的保留字可以不加引号当作键名。
1 var o = {?
2 for: 1, 3 ?class: 2 4 }; 5 6 o.for //1 7 o.class //2
2.3 对象属性
对象的每一个“键名”又称为“属性”(property),它的“键值”又称为属性值,可以是任何数据类型。如果一个属性值为函数,通常把这个属性称为“方法”,它可以像函数那样调用。
1 var o = {?
2 p: function(x) {?? 3 return 2 * x;? 4 } 5 }; 6 o.p(2) //4
上面对象申明了一个方法p,它就是一个函数。这里简单说一下,函数声明的三个步骤:function,函数名,函数参数,函数体。其中函数名和函数参数都是可选的,即也可以不使用。不使用的情况下称为匿名函数。
属性可以动态创建,不必在对象声明的时候就指定。
1 var obj = {};
2 obj.keith = 123;
3 obj.rascal = false; 4 obj.keith; // 123
因为对象的方法就是函数,所以也有name属性。
1 var obj = {?
2 m1: function f() {}, 3 ?m2: function() {} 4 }; 5 obj.m1.name // "f" 6 obj.m2.name // " " , 空字符串
2.4 对象引用
对于复杂数据类型,如果不同的变量名指向同一个对象,那么它们都是这个对象的引用,也就是说指向同一个内存地址。修改其中一个变量,会影响到其他所有变量。也就是 传址传递。
var o1 = {? a : 1};
var o2 = o1;
o1.a; // 1 o2.a; // 1 o2.a = 11; o1.a // 11
上面o1和o2都指向了同一个对象,当o2修改了o1的属性a时,访问o1的属性a变成11。复杂数据类型的传址传递的特点就是当修改其中一个变量,会影响到其他对象对该变量的访问。
此时,如果取消某一个变量对于原对象的引用,不会影响到另一个变量。
1 var o1 = {};
2 var o2 = o1; 3 var o1 = 1; 4 o2 // { }
上面代码中,o1和o2指向同一个对象,然后o1的值变为1,这时不会对o2产生影响,o2还是指向原来的那个对象。
但是,对于原始数据类型的值,则是传值传递。传值传递的特点就是修改其中一个变量,不会影响到其他变量。也就是只是对该变量copy一份而已。
1 var x = 1;
2 var y = x; 3 x = 2; 4 y; // 1
上面的代码中,全局变量x发生变化,y的值并不变。也就是上面所说的copy了x的值,没有指向同一个内存地址。
3 :对象属性
3.1:读取属性
1 var o = {
2 name: "Keith Chou",
3 born: "1995" 4 };
访问属性有两种方法。
1 o.name // "Keith Chou"
2 o["name"] // "Keith Chou"
第二种方法访问属性的时候必须加上引号,单引号双引号都可以。
3.2:属性的赋值
点运算符和方括号运算符,不仅可以用来读取值,还可以用来赋值。
1 var o = {};
2 o.p = "abc";
3 o["p"] = "abc";
3.3:查看所有属性
查看一个对象本身的所有属性,可以使用Object.keys 方法。
1 var o = {
2 "say": "Hello World",
3 "name": "Keith Chou", 4 "height": "180", 5 "weight": "120" 6 }; 7 Object.keys(o); 8 // ["say","name","height","weight"]
可以看出,js返回一个数组对象。
3.4:删除属性
Javascript使用delete来删除属性。delete操作符只能用来删除对象本身的属性,而不能用于删除继承自原型的属性。
1 var o = { p: 1 };
2 Object.keys(o);
3 // ["p"] 4 delete o.p; 5 o.p; 6 // undefined; 7 Object.keys(o); 8 // [ ]
delete删除了o对象的p属性。删除后,再次访问属性就会返回undefined。而且使用Object.keys访问对象属性时,o对象也不再包括任何属性。
toString()方法是对象o继承自原型Object.prototype的一个方法,虽然delete命令返回true,但该属性并没有被删除。
1 var o = {};
2 delete o.toString(); // true 3 o.toString();
注意,delele也可以用于删除一个不存在的属性,不过也不会报错,会返回true。不过这个看起来好像没有什么用处阿。
1 var o = {};
2 delete o.p // true
最后,delete操作符也不能用于删除var命令声明的变量,只能用来删除对象本身的属性。
1 var o = 1;
2 delete o; // false 3 delete window.o // false
上面代码中,o是在全局作用域下声明的一个全局变量,全局变量默认是window对象的属性,默认情况下delete不得删除。
3.5:遍历属性
for...in循环用来遍历一个对象的所有属性。
1 var o = {?
2 a: 1,
3 ?b: 2, 4 ?c: 3 5 };? 6 for (var i in o) {? 7 console.log(i); 8 } // a , b , c
上面代码中,定义了一个对象o,使用for..in循环来在控制台输出o对象中的每一个属性。 var i in o 是指 声明一个变量i,用于遍历o对象中的所有属性。
for...in循环有两个使用注意点:
-
- 它遍历的是所有对象可遍历的属性,会跳过不可遍历的属性。
- 它不仅会遍历对象自身的属性,还会遍历继承的属性。