浏览器对ES5的支持:
- IE8只支持defineProperty、getOwnPropertyDescriptor的部分特性和JSON的新特性
- IE9不支持严格模式, 其它都可以
- IE10和其他主流浏览器都支持了
- PC端开发需要注意IE9以下的兼容, 但移动端开发时不需要
一、严格模式
顾名思义,这种模式使得Javascript在更严格的语法条件下运行
严格模式的出现作用:
1. 消除Javascript语法的一些不合理、不严谨之处,减少一些怪异行为
2. 消除代码运行的一些不安全之处,保证代码运行的安全
3. 为未来新版本的Javascript做好铺垫
在使用严格模式的时候在全局或函数的第一条语句需定义为: ‘use strict’; 如果浏览器不支持, 只解析为一条简单的语句, 没有任何副作用
主要内容:
1. 必须用var声明变量(混杂模式中可以直接使用变量而不定义,但是这种做法会对后期造成很大的麻烦)
2. 创建eval作用域
var str='NBA';
eval('var str="cba"; alert(str)'); //解析传入的字符串
alert(str); //不使用严格模式,eval中的str会改变全局str的值,严格模式下
则只在eval作用域中修改str的值。即不使用严格模式弹出的分别是cba,cba;
使用严格模式弹出的是cba,NBA
3.禁止this指向window
//创建一个构造函数
function People(){
this.name=name;
this.age=age;
}
new People("xiaoming",18);
//必须要加new,不然函数是自调用,this指向的是window
4.对象不能用重名的属性
5.函数不能有重名的形参
二、json对象
JSON.stringify(obj/arr)
js对象(数组)转换为json对象(数组)
JSON.parse(json)
json对象(数组)转换为js对象(数组)
var obj={username:"mike"};
obj=JSON.stringify(obj);
console.log(typeof obj);
//json对象和数组,不要说json字符串
//json是一种传输数据的格式,还有xml。
三、object对象方法扩展
ES5给Object扩展了好一些静态方法, 常用的2个:
- Object.create(prototype[, descriptors]) : 创建一个新的对象
1). 以指定对象(prototype)为原型创建新的对象
2). 指定新的属性, 并对属性进行描述
value : 指定值
writable : 标识当前属性值是否是可修改的, 默认为true
get : 用来得到当前属性值的回调函数
set : 用来监视当前属性值变化的回调函数
var obj={username:"damu",age:30};
var obj1={};
obj1=Object.create(obj); //Object是obj1上一级的构造函数,调用他所具有的函数creat
console.log(obj1); //也就是obj1可以继承obj的属性username和age
var obj={username:"damu",age:30};
var obj1={};
obj1=Object.create(obj,{
sex:{
value:"男",
writable:true,//有一个writable属性:标识当前属性值是否是可以修改的,默认为false
configurable:true,//有一个属性configurable:标识当前属性是否可以被删除
enumerable:true //有一个属性enumerable:标识当前属性是否能用for in枚举 默认为false
}
} //对当前扩展属性的描述
}); //使用create给obj1添加扩展属性
console.log(obj1.sex);
obj1.sex="女"
console.log(obj1.sex);
delete obj1.sex;//规定不能直接删掉,有一个属性configurable:标识当前属性是否可以被删除,默认为false
console.log(obj1.sex);
for(var i in obj1){
console.log(i)//for in 找不到obj1使用create扩展出来的属性
//有一个属性enumerable:标识当前属性是否能用for in枚举 默认为false
}
- Object.defineProperties(object,descriptors)
作用:为指定object对象定义扩展多个属性
get:用来获取当前属性值的回调函数
set:修改当前属性值的触发的回调函数,并且实参即为修改后的值
存取器属性:setter,getter一个用来存值一个用来取值
var obj2={firstName:"kobe",lastName:"bryant"};
Object.defineProperties(obj2,{
fullName:{
get:function () {//使用get来获取扩展属性的值
return this.firstName+" "+this.lastName//fullName想要设置的值
},
set:function (data) {//监听扩展属性,当扩展属性发生变化时自动调用后会将变化的值作为实参注入到set函数。
console.log("set()",data);
var names=data.split(" ");
this.firstName=names[0];
this.lastName=names[1];
}
}//创建一个配置对象
})
console.log(obj2.fullName)
obj2.fullName="haha heih";
console.log(obj2.fullName)
//get方法什么时候调用? 获取扩展属性值的时候,get方法自动调用
//对象本身的两个方法:
//get propertyName(){}
//set propertyName(){}
var objj={
age:15,
tall:180,
get all(){
return this.age+" "+this.tall;
},
set all(data){
console.log("set()",data);
var names=data.split(" ");
this.age=names[0];
this.tall=names[1];
}
}
console.log(objj);
objj.all="13 189";
console.log(objj);
四、数组扩展
1.Array.prototype.indexOf(value):得到值在数组中的第一个下标,输入第一个3的下标
2.Array.prototype.lastIndexOf(value):得到值在数组中的最后一个下标
3.Array.prototype.forEach(function(item,index){}):遍历数组
4.Array.prototype.map(function(item,index){}):遍历数组返回一个新的数组,返回加工之后的值
5.Array.prototype.filter(function(item,index){}):遍历过滤出一个新的子数组,返回条件为true的值
var arr=[2,3,5,1,4,6,3];
console.log(arr.indexOf(3)); //输出第一个6的下标
console.log(arr.lastIndexOf(3)); //输出最后一个6的下标
arr.forEach(function(item,index){
console.log(item+" "+index) //输出所有元素的值和下标
})
var arr1=arr.map(function(item,index){
return item+10;
});
console.log(arr1); //根据arr产生一个新数组,要求每个元素比原来大10
var arr2=arr.filter(function(item,index){
return item > 4;
})
console.log(arr2); //根据arr产生一个新数组,返回的每个元素都要大于4
五、bind()、call()、apply()的区别
call和apply绑定this一个在后面传一个要求放在数组里
var obj={username:"kobe"};
function foo(data){
console.log(this,data)
}
// foo();
//自调用时this指向的是window,使this指向我们定义的obj
foo.call(obj);
foo.apply(obj);
//call和apply在不传参的情况下使用方式是一样的
//区别
function foo(data){
console.log(this,data)
}
foo.call(obj,33); //直接传入参数
foo.apply(obj,[33]); //传入数据必须写在数组里
//bind
var bar=foo.bind(obj,33);//绑定完this有一个返回值,不会立即调用当前函数而是将函数返回,通常用来指定回调函数的this。用bar来接收返回的函数然后执行
bar();
// 也可写成foo.bind(obj,33)()