ES6新特性(上篇)

let基本用法

ES6 新增了let命令,用来声明变量。它的用法类似于var。

let a = 10;
var b = 10;
console.log(a,b);//10 10

上面代码中,分别用let、var声明了变量,然后调用这两个变量,都能得到正确的值,但是两者之间还有区别的,如下例所示:

{
let c = 10;
var d = 10;
}
console.log(d); //10
console.log(c);  //c is not defined

上面代码中分别用let、var声明了变量,在代码块外面调用,结果let声明的变量报错,var声明的变量返回了正确的值。这表明,let声明的变量只在它所在的代码块有效。
注意:变量名命名规则
● 见名知义
● 不能使用关键字与保留字
● 遵循驼峰标识
● 变量名不能重(会报错)

let不存在变量提升

var命令会发生”变量提升“现象,即变量可以在声明之前使用,值为undefined。这种现象多多少少是有些奇怪的,按照一般的逻辑,变量应该在声明语句之后才可以使用。为了纠正这种现象,let命令改变了语法行为,它所声明的变量一定要在声明后使用,否则报错。

//var
console.log(a);  //undefined
var a = 10;

//let
console.log(b); // b is not defined
let b = 10;

上面代码中,变量a用var命令声明,会发生变量提升,即脚本开始运行时,变量a已经存在了,但是没有值,所以会输出undefined。变量b用let命令声明,不会发生变量提升。这表示在声明它之前,变量b是不存在的,这时如果用到它,就会抛出一个错误。
块级作用域
let实际上为 JavaScript 新增了块级作用域。

function f1() {
    let n = 5;
    if (true) {
        let n = 10;
    }
    console.log(n); // 5
}
f1();

上面的两个代码块中都声明了变量变量n,最后调用函数输出的结果为5,这表示外层代码块不受内层代码块的影响,如果使用var声明变量,则结果为10。
块级作用域允许任意嵌套,外层作用域无法读取内层作用域的变量,而且内外层作用域可以声明同名变量。

 {
        let a = 'admin'
        console.log(a,1111);
        {
            let a = 'ujiuye'
            console.log(a,222);
        }
    }

   // console.log(a)//a is not defined
const基本用法

const声明的常量,后期不能修改常量的值,并且在声明的同时要立刻初始化,不能后面赋值,其声明常量的作用域与let相同,在代码块内有效,在声明前调用变量报错,即const声明的常量不存在变量提升。

//1.常量 const声明的常量,不能修改该常量的值
const PI = 3.1414;
console.log(PI);
PI = 3;    //Assignment to constant variable
console.log(PI);
//2.用const声明的常量,需要立即初始化,不能留到后面赋值
const a; //Missing initializer in const declaration
//3.作用域与let相同,在代码块内有效
if(true){
    const block = 10;
}
console.log(block); //block is not defined
//4.const声明的常量也不存在常量提升
console.log(up); // up is not defined
const up = 10;
模板字符串

传统JavaScript输出模板通常是:

var n = 10;
$("p").append("there are <b>"+n+"</b>"+
                "ujiuye IT"+
                "<em>"+n+"</em>");

这种写法相当繁琐不方便,如果字符串特别长的时候也许还会弄错+和“”的位置,es6引入了模板字符串来解决这个问题。模板字符串是增强版字符串,用反引号`表示,里面的变量用${}包起来就可以实现。

var n = 10;
$("div").append(`there are <b>${n}</b>`);
它可以当作普通字符串使用,也可以用来定义多行字符串,或者在字符串中嵌入变量。在模板中嵌入变量需要将变量名写在${}中。
var str = `string text line 1
             string text line 2`;
console.log(str);
console.log(`${n}`);

关于${}中的值:
1.变量
2.任意javascript表达式
3.获取对象的属性
4.调用函数

简化的对象写法

ES6 允许直接写入变量和函数,作为对象的属性和方法。这样的书写更加简洁。

let foo = 'bar';
let baz = {foo};
baz // {foo: "bar"}
// 等同于
const baz = {foo: foo};
除了属性简写,方法也可以简写。
const o = {
  method() {
    return "Hello!";
  }
};

// 等同于

const o = {
  method: function() {
    return "Hello!";
  }
};

注意:方法简写时,和普通方法的特性是一样的,主要体现在this。

箭头函数

es6允许用箭头(=>)声明函数,更加快捷方便。()=>{}等价于function (){}。
箭头函数与简单函数的区别
没有参数时
语法:变量名 = ()=>{函数体}

//1.没有参数的情况  ()=>{}
var f =()=>{
    console.log("10"); //"10"
}
f();

有参数时
语法:变量名=(参数1,参数2)=>{函数体},如果只有一个参数,可以将()省略,两个或两个以上参数不能省略(),每个参数之间用’,’隔开。

//2.一个参数的情况
var f = n =>{
    var sum = 0;
    for(let i = 0;i <= n;i++){
        sum += i;
    }
    console.log(sum); //5050
}
f(100);

多个参数的情况,不能省略(),多个参数之间用,隔开

var f4 = (n,m)=>{
    console.log(n*m);
}
f4(10,20);

es5写的函数,都可以用es6的箭头函数表示出来。

有返回值时
语法:变量名 = (参数)=>{return 返回值}

//普通函数返回值
function fun5(n,m) {
    return n*m;
}
console.log(fun5(2,3)); //6
//箭头函数返回值
var fu = (n,m)=>{
    return n*m;
}
console.log(fu(10,20)); //200

如果函数体中就一条语句,可以省略大括号{},如果这一条语句是返回值,还可以省略return关键字。

//1.如果函数体中就一条语句,可以省略{}
var f =n=> console.log(n); //10
console.log(f(10)); 
//2.如果这一条语句是返回值,则还可以省略return关键字
var f1 =(n,m)=> n*m; //省略return
console.log(f1(10,20)); //200

箭头函数中的this
全局函数的中的this

//1.在window中定义,this指向window
function fun(){
    console.log(this); //window
}
fun();
var fun1 = n =>{
    console.log(this); //window
}
fun1();

Window中声明的函数,es5和es6中的this都指向window。

事件处理函数中的this

var oDiv = document.getElementById("box");
oDiv.onclick = function () {
    console.log(this); //div
}
oDiv.onclick = ()=>{
    console.log(this); //window
}

如果是作为事件处理函数,es5中的this指向的是当前触发事件的对象,es6中的this指向的是window。

对象方法中的this

//在构造函数中给对象添加了eat方法,调用这个方法会返回一个函数
function  Person() {
    this.eat = function () {
        return function () {
            console.log(this);
        }
    }
}
var p = new Person();
p.eat()(); //函数返回到外面,全局调用,this-->window
//箭头函数里面的this,在那定义就指向谁
function  Dog() {
    this.eat = function () {
        return ()=>{
            console.log(this);
        }
    }
}
var d = new Dog();
d.eat()();  //在Dog构造函数里面调用,this--->Dog

函数声明在对象方法中,es5中因为函数传出到全局所以指向的是window,es6中函数在那定义的就指向谁,所以this指向Dog。
箭头函数注意点
箭头函数有以下几点是需要注意的:
1.函数体内的this对象,就是定义时所在的对象,而不是使用时所在的对象。
2.不可以当作构造函数,也就是说,不可以使用new命令,否则会抛出一个错误
3.不可以使用arguments对象,该对象在函数体内不存在。如果要用,可以用rest参数(后面讲解)代替。

this对象
函数体内的this对象,就是定义时所在的对象,而不是使用时所在的对象。

function  Dog() {
    this.eat = function () {
        return ()=>{
            console.log(this);
        }
    }
}
var d = new Dog();
d.eat()();  //在Dog构造函数里面调用,this--->Dog

不能作为构造数
不可以当作构造函数,也就是说,不可以使用new命令,否则会抛出一个错误。

var Person = (name)=>{
    this.name = name;
}
var p1 =new Person("ujiuye");  //Person is not a constructor   不是构造函数
console.log(p1.name);

不可以使用arguments对象
不可以使用arguments对象,该对象在函数体内不存在。如果要用,可以用Rest参数代替。

var arg = (a,b,c,d)=>{
    console.log(arguments);  //arguments is not defined
}
arg(1,2,3,4);
var arg1 = (...num)=>{
    console.log(num); //[1, 2, 3, 4]
}
arg1(1,2,3,4);
扩展运算符

扩展运算符(spread)是三个点(…)。它好比 rest 参数的逆运算,将一个数组转为用逗号分隔的参数序列。

//将一个数组转为用逗号分隔的参数序列。
console.log(...[1, 2, 3]); //1 2 3
console.log(1, ...[2, 3, 4], 5); //1 2 3 4 5
//一般用于函数调用
function add(x, y) {
    return x + y;
}
const numbers = [2,3];
console.log(add(...numbers)) // 5

扩展运算符的一般应用
可以复制数组,将类似数组转换为真正的数组

//1.复制数组
const a1 = [1, 2];
const a2 = [...a1];
//2.将类似数组转为真正的数组
console.log([...'hello']); //["h", "e", "l", "l", "o"]
console.log([..."𠮷"].length);//1能够正确识别四个字节的 Unicode 字符
var oDiv = document.getElementsByTagName("div");
console.log([...oDiv]); //[div, div, div]
函数默认值

ES6 之前,不能直接为函数的参数指定默认值,只能采用变通的方法。

function log(x, y) {
  y = y || 'World';
  console.log(x, y);
}

log('Hello') // Hello World
log('Hello', 'China') // Hello China
log('Hello', '') // Hello World

上面代码检查函数log的参数y有没有赋值,如果没有,则指定默认值为World。这种写法的缺点在于,如果参数y赋值了,但是对应的布尔值为false,则该赋值不起作用。就像上面代码的最后一行,参数y等于空字符,结果被改为默认值。
ES6 允许为函数的参数设置默认值,即直接写在参数定义的后面。

function log(x, y = 'World') {
  console.log(x, y);
}

log('Hello') // Hello World
log('Hello', 'China') // Hello China
log('Hello', '') // Hello

除了简洁,ES6 的写法还有两个好处:首先,阅读代码的人,可以立刻意识到哪些参数是可以省略的,不用查看函数体或文档;其次,有利于将来的代码优化,即使未来的版本在对外接口中,彻底拿掉这个参数,也不会导致以前的代码无法运行。

参数变量是默认声明的,所以不能用let或const再次声明。

function foo(x = 5) {
  let x = 1; // error
  const x = 2; // error
}

以上是我对ES6新特性上部分的理解,中下部分将在后续两篇文章中详细讲解,欢迎大家互相交流!

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值