ES5的学习记录
提示:根据视频学习的一些记录
文章目录
一、day1的学习内容
1.严格模式
语法和行为的改变:
* 必须使用 var 声明变量;
* 禁止使用自定义函数中的 this 指向 window
* 创建 eval 作用域(防止污染全局变量)
* 对象不能有重名的属性
1).必须使用 var 声明变量
<script type="text/javascript">
// 'use strict';
username = 'xiaochen';
console.log(username);
</script>
结果:浏览器会显示 xiaochen
<script type="text/javascript">
'use strict';
username = 'xiaochen';
console.log(username);
</script>
结果就会报如下错误:
2).禁止使用自定义函数中的 this 指向 window
<script type="text/javascript">
// 'use strict';
function Person(name,age){
this.name = name;
this.age = age;
}
Person('xiaochen',19);
</script>
结果:浏览器不会报错
<script type="text/javascript">
// 'use strict';
function Person(name,age){
this.name = name;
this.age = age;
}
new Person('xiaochen',19);
</script>
结果就会报错:
3).创建 eval 作用域(防止污染全局变量)
<script type="text/javascript">
//'use strict';
var str = 'xixixi'
eval('alert(str)'); //xixixi
</script>
结果:浏览器会弹出 xixixi
<script type="text/javascript">
//'use strict';
var str = 'xixixi'
eval('var str = "hahaha";alert(str)'); //hahaha
alert(str); //xixixi
</script>
结果会先弹出:hahaha 后面会弹出:hahaha
如果使用严格模式:
就会先弹出:hahaha 后弹出:xixixi
这样呢就不会污染全局变量,定义了 eval 函数的作用域
4).对象不能有重名的属性
这个呢就很好理解,一般编译器在重复命名的时候,就会报错。
2.JSON对象
1.JOSN.stringify(obj/arr)
* js对象(数组)转换成josn对象(数组)
2.JOSN.parse(json)
* json对象(数组)转换成js对象(数组)
<script type="text/javascript">
var obj = {username:'xiaochen'};
obj = JSON.stringify(obj);
console.log(typeof obj);
obj = JSON.parse(obj);
console.log(typeof obj);
</script>
3.Object扩展
ES5给Object扩展了一下静态方法,常用的两个:
1.Object.create(prototype,[descriptors])
*作用:以指定对象为原型创建新的对象
*为新的对象指定新的属性,并对属性进行描述
- value:指定值
- writable:表示当前属性是否是可修改的,默认为false
- configurable: 表示当前属性是否可以被删除,默认为false
- enumerable:表示当前属性是否能用 for in 枚举,默认false
2.Object.defineProperties(object,descriptors)
*作用:为指定对象定义扩展多个属性
- get:用来获取当前属性值得回调函数
- set:修改当前属性值得触发的回调函数,并且实参为修改后的值
- 存取器属性:setter,getter一个用来存值,一个用来取值
第一点知识的代码理解:
<script type="text/javascript">
var obj = {username:'xiaochen',age:30};
var obj1 = {};
obj1 = Object.create(obj,{
sex:{
value:'男',
writable:true,
configurable:true,
enumerable:true
}
});
console.log(obj1);
console.log(obj1.sex);
obj1.sex = '女';
console.log(obj1.sex); //因为设置了writable属性,所以才可以修改
delete obj1.sex;
console.log(obj1);//因为设置了configurable属性,所以才可以删除
for(var i in obj1){ //因为设置了enumerable属性,所以才可以枚举
console.log(i);
}
</script>
其中打印的结果如下:
可以看到对象obj1是带有隐式原型的其中的_proto_便是。
第二点知识讲解:
<script type="text/javascript">
//Object.defineProperties(object,descriptors)
var obj2 = {firstName:'kobe',lastName:'bryant'};
Object.defineProperties(obj2,{
fullName:{
get:function(){//获取属性的值,获取扩展属性值得get方法自动调用
return this.firstName + ' ' + this.lastName;
},
set: function(data){//监听扩展属性,当扩展属性发生变化的时候会自动调用,自动调用后会将变化的值作为实参注入到set函数
var names = data.split(' ');
this.firstName = names[0];
this.lastName = names[1];
}
}
});
console.log(obj2.fullName);
obj2.fullName = 'tim duncan';
console.log(obj2);
</script>
这里有一个需要注意到的点是,在浏览器看到的如下图所示的大括号里面的点点点,点击后就会显示fullName,这个就是惰性求值,这个时候其实就是使用了这个get方法,可以在方法体里面打印一下,就可以看出来。
同时对象本身也有两个方法:
<body>
<!--
对象本身的两个方法
* get propertyName(){} 用来得到当前属性值的回调函数
* set propertyName(){} 用来监视当前属性值变化的回调函数
-->
</body>
<script type="text/javascript">
var obj = {
firstName:'curry',
lastName:'stephen',
get fullName(){
return this.firstName + ' ' + this.lastName;
},
set fullName(data){
names = data.split(' ');
this.firstName = names[0];
this.lastName = names[1];
}
}
console.log(obj);
obj.fullName = 'kobe bryant';
console.log(obj.fullName);
</script>
4.Array扩展
<body>
<!--
Array.prototype.indexOf(value):得到值在数组中的第一个下标
Array.prototype.lastIndexOf(value):得到值在数组中的最后一个下标
Array.prototype.forEach(function(item,index){}):遍历数组
Array.prototype.map(function(item,index){}):遍历数组返回一个新的数组,返回加工之后的值
Array.prototype.filter(function(item,index){}):遍历过滤出一个新的子数组,返回条件为true的值
-->
</body>
<script type="text/javascript">
var arr = [2,4,3,1,2,6,5,4];
console.log(arr.indexOf(4));
console.log(arr.lastIndexOf(4));
arr.forEach(function(item,index){
console.log(item,index);
})
var arr1 = arr.map(function(item,index){
return item + 10;
})
console.log(arr,arr1);
var arr2 = arr.filter(function(item,index){
return item >= 4
})
console.log(arr,arr2);
</script>
控制台返回结果:
5.Function扩展
1.Function.prototype.bind(obj):
*作用:将函数内的this绑定为obj,并将函数返回
2.面试题:区别bind()与call()和apply()?
* 都能指定函数中的this
* call()/apply()是立即调用函数
* bind()是将函数返回
<script type="text/javascript">
var obj = {username:'xiaochen'};
function foo(data){
console.log(this,data);
}
// 传入参数的形式
foo.call(obj,33); //直接从第二个参数开始,依次传入
foo.apply(obj,[33]); //第二个参数必须是数组,传入放在数组里
//bind的特点:绑定完this不会立即调用当前的函数,而是将函数返回
//bind传参的方式同call一样
// var bar = foo.bind(obj,33);
// console.log(bar); //会发现这是个方法
// bar(); //函数调用
//上面这个三行等价于下面这一行
foo.bind(obj,33)();
setTimeout(function () {
console.log(this);
}.bind(obj), 1000);
</script>
控制台返回结果: