JavaScript总结:
JavaScript总结有一下几点:数组的遍历,作用域,闭包,this指向。
1.数组的遍历
1.1使用for和for/in,我们可以访问数组的下标,而不是实际的数组元素值:
for(var i = 0; i < arr.length; ++i){
console.log(arr[i]);
}
for(var i in arr){
console.log(arr[i]);
}
1.2使用for/of,则可以直接访问数组的元素值:
for(const v of arr){
console.log(v);
}
1.3使用forEach(),则可以同时访问数组的下标与元素值:
arr.forEach((v,i) => console.log(v));
2.作用域
var a = 1;
function test(){
var a = 2;
console.log(a); //2
}
test();
上方的函数作用域中声明并赋值了a,且在console之上,所以遵循就近原则输出a等于2。
var a = 1;
function test2(){
console.log(a); //undefined
var a = 2;
}
test2();
上方函数作用域中虽然声明并赋值了a,但位于console之下,a变量被提升,输出时已声明但尚未被赋值,所以输出“undefined“。
var a = 1;
function test3(){
console.log(a); //1
a = 2;
}
test3();
上方的函数作用域中a被重新赋值,未被重新声明,且位于console之下,所以输出全局作用域中的a。
3.闭包
var elem = document.getElementsByTagName('div'); //如果页面上有5个div
for(var i = 0; i < elem.length; i++){
elem[i].onclick = function(){
alert(i); //总是5
};
}
上方是一个很常见闭包问题,点击任何div弹出的值总是5,因为当你触发点击事件的时候i的值早已是5,可以用下面方式解决:
var elem = document.getElementsByTagName('div'); //如果页面上有5个div
for(var i = 0; i < elem.length;i++){
(function (w) {
elem[w].onclick = function(){
alert(w); //依次为0,1,2,3,4
};
})(i);
}
在绑定点击事件外部封装一个立即执行函数,并将i传入该函数即可。
4.this指向
var obj = {
name: 'xiaoming',
getName: function(){
return this.name;
}
};
console.log(obj.getName()); //'xiaoming'
上方对象方法中的this指向对象本身,所以输出”xiaoming“。
var obj = {
myName: 'xiaoming',
getName: function(){
return this.myName;
}
};
var nameFn = obj.getName;
console.log(nameFn()); //undefined
上方将对象中的方法赋值给了一个变量,此时方法中的this也将不在指向obj对象,从而指向window对象,所以console为”undefined“。
var obj = {
myName: 'xiaoming',
getName: function(){
return this.myName;
}
};
var obj2 = {
myName: 'xiaohua'
};
var nameFn = obj.getName;
console.log(nameFn.apply(obj2));//'xiaohua'
上方同样将obj对象中的方法赋值给了变量nameFn,但是通过apply方法将this指向了obj2对象,所以最终console为’xiaohua’。
ES6总结:
1.let和const命令
let用来声明变量,只在let命令所在的代码块中有效。
{
let a =10;
var b = 1;
}
a // ReferenceError: a is not
b // 1
表明:let声明的变量只在它所在的代码块有效。
const命令
基本规则:
- 声明只读常量
- 一旦声明必须赋值,不赋值,会报错。
- const的作用域只在声明的块级域内有效。
- 声明的常量不提升,存在暂时性死区,只能在声明的位置后面使用
- const声明的常量,与let一样不可重复声明
const PI = 3.1415;
PI //3.1415
PI = 3;
//TypeError:Assignment to constant variable.
2.解构赋值
解构赋值语法是一种JavaScript表达式,用来将数组中的值或对象中的属性取出来区分为不同变量。
2.1、变量声明并赋值时的解构
var foo = ["one","two","three"];
var [one,two,three] = foo;
console.log(one);//"one"
console.log(two);//"two"
console.log(three);//"three"
2.2、变量先声明后赋值时的解构
通过解构分离变量的声明,可以为一个变量赋值。
var a,b;
[a,b] = [1,2];
console.log(a);//1
console.log(b);//2
2.3、默认值
为了防止从数组中取出一个值为undefined的对象,可以在表达式左边的数组中为任意对象预设默认值。
var a,b;
[a=5,b=7] = [1];
console.log(a);//1
console.log(b);//7
2.4、交换变量
在一个解构表达式中可以交换两个变量的值。没有解构赋值的情况下,交换两个变量需要一个临时变量。
var a = 1;
var b = 3;
[a,b] = [b,a];
console.log(a);//3
console.log(b);//1
2.5、解析一个从函数返回的数组
从一个函数返回一个数组是十分常见的情况。解构使得处理返回值为数组时更加方便。
function f(){
return [1,2];
}
var a,b;
[a,b] = f();
console.log(a);//1
console.log(b);//2
2.6、将剩余数组赋值给一个变量
当解构一个数组时,可以使用剩余模式,将数组剩余部分赋值给一个变量。
var [a,...b] = [1,2,3];
console.log(a);//1
console.log(b);//[2,3]
2.7、for循环解构
var arr = [[11,12],[21,22],[31,32]];
for(let [a,b] of arr){
console.log(a);
console.log(b);
}
//11
//12
//21
//22
//31
//32
3.箭头函数
ES6增加了箭头函数:
let func = value => value;
相当于:
let func = function(value){
return value;
};
如果需要给函数传入多个参数:
let func = (value,num) => value * num;
如果函数的代码块需要多条语句:
let func = (value,num) =>{
return value * num
};
如果需要直接返回一个对象:
let func = (value,num) =>({total:value*num});
与变量解构结合:
let func = ({value,num}) => ({total: value*num})
//使用
var result = func({
value: 10,
num: 10
})
console.log(result);//{total:100}
4.数组
4.1、Array.from(json)
将json字符串转为数组,json字符串务必要有长度属性
let json ={
'0': 'niit',
'1': 'computer',
'2': 'mobile',
length: 3
}
let arr1 = Array.from(json);
console.log(arr1);
function test(a,b){
let arr = Array.from(arguments,value => value +2);
console.log(arr);
}
test(1,2);
4.2、Array.of(变量)
将变量转为数组,可以不要在使用eval进行转换,替代Array()或new Array()
let arr2 = Array.of(1,2,3,4);
console.log('arr2:',arr2);
4.3、fill()
使用给定值填充数组,数组中的原有元素会被抹去,从位置start开始填充,不包含end位置
let arr4 = [1,2,3,4,5,6,7,8,9];
arr4.fill(1,2,5);
console.log(arr4);
4.4、map()
原来数组有多少个,map处理之后还是那么多个。
语法:arr.map(fn,thisArg)
let arr = [12,35,56,79,56];;
let arr1 = arr.map(item => item%2 === 0 ?'偶' : '奇');
let arr2 = arr.map((item,index) => index+':'+item);
console.log(arr);
console.log(arr1);
console.log(arr2);
4.5、reduce()
reduce()方法接收一个方法作为累加器,数组中的每个值(从左至右)开始合并,最终为一个值。
语法:arr.reduce(fn,initialValue)
var arr = [1,2,3,4];
arr.reduce((previousValue,value,index,array) => {
console.log(previousValue);
console.log(value);
console.log(index);
return previousValue+value;//10
})
4.6、filter()
filter()方法使用传入的函数测试所有元素,并返回所有通过测试的元素组成的新数组。它就好比一个过滤器,筛掉不符合条件的元素
语法:arr.filter(fn,thisArg)
var arr = [1,2,3,4];
arr.filter((value,index,array) =>{
return value >2
})
4.7、forEach()
forEach()方法指定数组的每项元素都执行一次传入的函数,返回值为undefined。
语法:arr.forEach(fn,thisArg);
let scores = [23,45,76,85,12,91];
scores.forEach((item,index) =>{
console.log(`第${index}个元素`+`是`+item);
})