JavaScript创建对象和属性的查询和设置
JavaScript 对象
JavaScript 中的所有事物都是对象:字符串、数值、数组、函数...
JavaScript 提供多个内建对象,比如 String、Date、Array 等等。 对象只是带有属性和方法的特殊数据类型。
- 布尔型可以是一个对象。
- 数字型可以是一个对象。
- 字符串也可以是一个对象
- 日期是一个对象
- 数学和正则表达式也是对象
- 数组是一个对象
- 函数也可以是对象
js数据类型
1 var str = 'str'; #字符串 2 var num = 123; #数值 3 var bool = true; #布尔 4 var n = null; #null 5 var unde = undefined; #undefined 6 var arr=[1,2,3,4,5]; #数组 7 var obj = {name:'sonia'}; #对象 8 var f = function(){}; #函数 9 console.log(typeof str); //string 10 console.log(typeof num); //nember 11 console.log(typeof bool); //boolean 12 console.log(typeof n); //object 13 console.log(typeof unde); //undefined 14 console.log(typeof obj); //object 15 console.log(typeof f); //function
object类型对象创建
第一种object构造函数
优点:较直观看到对象的属性和方法
缺点:处理多个类型,需要创建多个实例
1 var obj = new Object(); 2 obj.name="abc"; 3 obj.action = function() { 4 console.log(this.name) 5 }; 6 console.log(obj.name); //abc 7 obj.action(); //abc
第二种字面量
优点:便于封装调用
缺点:只能创建一次对象,复用性较差
1 1)简单的字面量 2 var obj2 = {}; 3 obj2.name ='jss'; 4 obj2.age = 21; 5 obj2.action = function(){ 6 return this.age;//this表示当前obj2对象
7 } 8 9 10 2)嵌套字面量(推荐使用) 11 var obj3 = { 12 name:'jack', 13 age:18, 14 action:function(){ 15 return this.name; 16 } 17 }
第三种工厂方式
优点:解决了重复创建相识对象的问题
缺点:工厂模式虽然解决了创建多个相似对象的问题,但却没有解决对象识别的问题(即怎样知道一个对象的类型)。
1 function createObj(name) { 2 var obj4 = new Object(); 3 obj4.name = name; 4 obj4.action = function(){ 5 console.log(this.name) 6 }; 7 return obj4; 8 } 9 var a = createObj('衣服'); 10 var b = createObj('鞋子'); 11 12 a.name //衣服
第四种构造函数 首字母大写 驼峰命名
构造函数:构造函数与其他函数的唯一区别,就在于调用它们的方式不同。不过,构造函数毕竟也是函数,不存在定义构造函数的特殊语法。任何函数,只要通过 new 操作符来调用,那它就可以作为构造函数;
按照惯例,构造函数始终都应该以一个大写字母开头,而非构造函数则应该以一个小写字母开头。
优点:明确了实例对象,
缺点:使用构造函数的主要问题,就是每个方法都要在每个实例上重新创建一遍。在下面的例子中,p3和 p4 都有一个名为 action()的方法,但那两个方法不是同一个 Function 的实例.因此,不同实例上的同名函数是不相等的.
1 function Person(name,age){ 2 this.name = name; //构造函数中this指向当前实例化对象
3 this.age = age; 4 this.action = function(){ //this.action = new Function("alert(this.name)"); 与声明函数在逻辑上是等价的 5 console.log(this.name); 6 } 7 }; 8 var p3 = new Person('abc',20); 9 var p4 = new Person('xyz',20); 10 console.log(p3 instanceof Person);//true
改进后:
我们把 action()函数的定义转移到了构造函数外部。而在构造函数内部,我们
将 action属性设置成等于全局的 action函数。这样一来,由于 action包含的是一个指向函数
的指针,因此 p3 和 p4对象就共享了在全局作用域中定义的同一个 action()函数。
缺点:
如果对象需要定义很多方法,那么就要定义很多个全局函数,于是我们这个自定义的引用类型就丝毫没有封装性可言了。好在,这些问题可以通过使用原型模式来解决。
1 function Person(name,age){ 2 this.name = name; 3 this.age = age; 4 this.action = action; 5 }; 6 function action(){ 7 console.log(this.name); 8 }; 9 var p3 = new Person('abc',20); 10 var p4 = new Person('xyz',20); 11 console.log(p3 instanceof Person);
原型模式+构造函数
我们创建的每个函数都有一个 prototype(原型)属性,这个属性是一个指针,指向一个对象,而这个对象的用途是包含可以由特定类型的所有实例共享的属性和方法。
1 function Person(name,age){ 2 this.name = name; 3 this.age = age; 4 // this.action = function(){ 5 // console.log('大家都要睡觉'); 6 // } 7 }; 8 Person.prototype.action = function(){ 9 console.log('大家都要睡觉'); 10 } 11 var p5 = new Person('abc',20); 12 var p6 = new Person('xyz',20); 13 p5.action(); //大家都要睡觉
对象的属性
设置/获取属性 . / [ ]
区别:.是取自身的属性 [ ]可以是变量
1 var obj = {} 2 obj.name = 'abc'; 3 obj['age']= 18; 4 console.log(obj.name); 5 console.log(obj['name']); 6 //实例 7 var o = { 8 name:'xyz', 9 age:18 10 } 11 var a = 'name'; 12 console.log(o[a]) //o[a]===o['name'] o.a则会打印undefined
删除属性
通过关键字delete 对象.属性 就可以删除
1 var o2 = { 2 name:'xyz', 3 age:18 4 } 5 //delete o2.name; 6 delete o2['name']; 7 console.log(o2); //{age: 18} name已经没了
属性的检测
属性检测有三种方法
1)用 in 运算符 判断对象中的属性是否存在
1 var o4 ={a:'1',b:'2',c:'3'}; 2 console.log('a' in o4); //true 3 console.log('m' in o4); //false
2)使用对象的hasOwnProperty()方法
1 var o4 ={a:'1',b:'2',c:'3'}; 2 console.log(o4.hasOwnProperty('a')); //true 3 var type = 'b'; 4 console.log(o4.hasOwnProperty(type)); //true
3)使用 !=undefined 判断
var o4 ={a:'1',b:'2',c:'3'}; console.log(o4.a != undefined) //true 说明a它存在o4中 var o5 = {a:undefined} console.log(o5.a != undefined) //false 这里有点注意的是使用这个方法,字段值就不能是undefined
属性的遍历
1 // for ... in 2 var o5 ={a:'1',b:'2',c:'3'}; 3 var arr = ['x','y','z','w']; 4 //对象 获取到属性的key 5 for(var k in o5){ //o5对象 k变量 6 //console.log(k) //a b c 7 console.log(o5[k]) //123 8 }; 9 //数组 获取索引 10 for(var v in arr){ 11 console.log(v) //0123 12 }; 13 14 for(var i=0;i<arr.length;i++){ 15 console.log(arr[i]); 16 }; 17 18 //forEach 没有返回值 19 var arr = ['x','y','z','w']; 20 arr.forEach(function(item,index,input){ //item 当前元素 index索引 input ['x','y','z','w'] 21 console.log(index) 22 }); 23 24 //map 回调函数中支持return返回值 25 var arr = ['x','y','z','w']; 26 var a = arr.map(function(item,index,input){ //item 当前元素 index索引 input ['x','y','z','w'] 27 return item+'1'; 28 }); 29 console.log(a);