Web前端系列技术之JavaScript进阶(从ES6开始)②

ES6 基础学习二

国庆这几天假期,博主我临时有些事情,所以连文章都没有更新,实在是惭愧啊,回头看了看博客,是真心很感谢那些陪伴着我没有取关的粉丝们呀

❤️❤️谢谢各位!!!

在之前的内容学习中,已经学会了基础的 DOM操作BOM操作 ,同时也认识了 对象函数事件 的基本概念和用法,有兴趣的小伙伴可以❤️ 订阅APIs专栏免费学习 ❤️哟;那么接下来就是会结合目前市面上最流行的 ES6 对这些 基础的JS 进行更细化的学习;


说到 ES6 ,这已经是第二天学习了,我想大家多少在第一章中有所了解; 那么学习 ES6 主要学习的就是耳熟能详的 Promise箭头函数模板字符串 、以及 let解构,当然也包括陌生的 代理反射迭代器生成器 等,欢迎大家 订阅关注 啦❤️❤️

那么今天主要会学习的内容是:
一、解构赋值
二、面向对象
三、引用类型


文章目录

  • ES6 基础学习二
  • 一、解构赋值
    • 1. 数组解构
    • 2. 对象解构
  • 二、面向对象
    • 1. 创建对象
    • 2. 构造函数
      • 2.1 内置构造函数方法
      • 2.2 自定义构造函数方法
      • 2.3 实例对象与构造函数对象匹配检测
    • 3. 实例成员
    • 4. 静态成员
  • 三、引用类型
    • 1. Object对象
    • 2. Array数组
    • 3. RegExp正则
  • 总结


一、解构赋值

什么是解构,什么又是解构赋值?或许这里就有小伙伴开始疑惑了;

基础概念: 解构 是一种赋值语法,它可以从 数组中提取元素 或者是从 对象中提取属性,将其赋值给对应的变量或者是另外一个对象的属性;

目的: 简化提取数据的过程,增强代码的可读性。

简单理解:解构就是一种快速为变量赋值的简洁语法,本质上仍然是为变量赋值,分为数组解构对象解构两大类型;

二者的主要区别是:前者是数组字面量,后者是对象字面量

1. 数组解构

基础概念: 数组解构是将数组的单元值快速批量赋值给一系列变量的简洁语法;

代码样例:

// 一一对应
let [a, b, c, d, e, f] = ['张飞', '赵云', '关羽', '张辽', '许褚', '典韦']
console.log(a, b, c, d, e, f);

// 相互替换(变量声明后面的分号不能省略)
let a = '张飞' , b = '赵云';		
[ a , b ] = [ b , a ]

// 右侧非可迭代对象
let [ a , b ] = NaN;
let [ a , b ] = undefined; 
let [ a , b ] = null;

// 变量多值少
let [a, b, c, d, e, f, g, h, i, j, k,l] = ['张飞', '赵云', '关羽', '张辽', '许褚', '典韦'];
console.log( a, b, c, d, e, f, g, h, i, j, k, l );

// 变量少值多
let [a, b, c] = ['张飞', '赵云', '关羽', '张辽', '许褚', '典韦'];
console.log( a, b, c );
		
// 按需取值
let [, , a, b, , c] = ['张飞', '赵云', '关羽', '张辽', '许褚', '典韦']
console.log( a, b, c );
		
// 剩余值
let [, a, b, ...c] = ['张飞', '赵云', '关羽', '张辽', '许褚', '典韦'];
console.log(a, b, c);
		
// 复杂情况
let [, , a, b, [, c, d]] = ['张飞', '赵云', '关羽', '张辽', ['林冲', '鲁智深', '武松', '宋老板']]
console.log( a, b, c, d );

总结:

  1. 赋值运算符 = 左侧的 [] 用于批量声明变量,右侧数组的单元值将被赋值给左侧的变量,且右侧必须是可迭代对象,否则报错;
  2. 变量的 顺序对应 数组单元值的位置依次进行赋值操作;
  3. 变量的数量大于单元值数量时,多余的变量将被赋值为 undefined
  4. 变量的数量小于单元值数量时,可以通过 ... 获取 剩余单元值 ,但只能置于最末位;
  5. 允许初始化变量的默认值,且只有单元值为 undefined 时默认值才会生效;
  6. 支持多维解构赋值,如同上述的 复杂情况

⭐注意:数组解构时,会按照顺序作用于数组的元素上,也就是说,变量或对象的属性要取谁的值与它所在的位置有关;

2. 对象解构

基础概念: 对象解构是将对象属性和方法快速批量赋值给一系列变量的简洁语法;

代码样例:

// 原始方式
let obj = {
	uname : '张三丰',
	age : 22,
	sex : '男'
}
console.log( obj.uname, obj.sex );

// 解构赋值方式
let {uname, sex} = {
	uname : '小柴爱程序',
	age : 24,
	sex : '男'
}
console.log( uname, sex );

// 外部有同名变量情况:冒号改名字
let uname = '小柴';
let {uname:userName, sex} = {
	uname : '小柴爱程序',
	age : 24,
	sex : '男'
}
console.log( userName, sex );

// 同名属性情况
let {uname:userName, uname:sex} = {
	uname : '小柴爱程序',
	age : 24,
	sex : '男'
}
console.log( userName, sex );

// 复杂情况
let { dog:{uname} } = {
	uname : '小柴爱程序',
	dog : {
		uname : '柴犬',
		age : 1,
	},
	age : 22,
	sex : '男',
}
console.log( uname );

总结:

  1. 赋值运算符 = 左侧的 {} 用于批量声明变量,右侧对象的属性值将被赋值给左侧的变量;
  2. 对象属性的值将被赋值给与属性名相同的变量;
  3. 对象解构中允许出现多个同名属性;
  4. 对象中找不到与变量名一致的属性时变量值为 undefined,这就相当于变量的只声明未赋值;
  5. 允许初始化变量的默认值,属性不存在或单元值为 undefined 时默认值才会生效;
  6. 支持多维解构赋值;

⭐注意:

  1. 在对象解构时,对象的属性是没有按顺序排列的,所以解构对象的时候只会根据属性的名称是否相同来取直,因此重点需要记住【 把对象属性名当变量名处理 】;
  2. 如果对象外部已经存在同对象属性名相同的变量,那么就要用 冒号改名字 ——防止因外部有相同的变量名而导致变量冲突;

二、面向对象

在编程思想的世界中,往往被分为两大类:面向过程面向对象 ,它们往往针对于不同规模的开发项目,对于 大型项目 的开发通常会利用到 面向对象 ,而对于 小型项目 还是会选 取面向过程 的方式;

主要思想: 把构成问题的各个事务分解成各个对象,建立对象的目的不是为了完成一个步骤,而是为了描叙一个事物在整个解决问题的步骤中的行为;

这里首先要介绍的是:构造函数实例成员 、以及静态成员 ,在介绍之前,我们不得不需要搞清楚两个概念 【类】【对象】

  1. 类: 通俗一点说就是一类一种的概念、是一种宽泛的概念,譬如 CSDN博主就是一个类,因为有很多博主;
  2. 对象: 类中的具体的某个实例,譬如 名字叫小柴爱程序的CSDN博主就是一个对象,因为就只有一位这样的博主;

⭐注意:在JavaScript中,一切皆可成为对象;

1. 创建对象

在创建对象的方法中,往往被分为两种方式,一种是 字面量创建对象 ,一种是 构造函数创建对象

① 字面量创建方式:

let obj = {
    // 属性
    uname : '小柴',
    age : 24,
	sex : '男',
	// 方法
	taiji : function () {
        console.log('台球');
	},
}

// 访问方式
console.log( obj.uname );//用于固定属性写法
console.log( obj['age'] );//用于动态属性的写法

// 遍历方式(数组也可以)
for ( let key in obj ) {
	console.log( obj[key] );//要注意使用动态属性[]才行
}

② 构造函数创建方式:

// 定义函数
function obj() {
   console.log('通过 new 也能调用函数...');
}
// 调用函数
new obj;

2. 构造函数

基础概念: 构造函数是专门用于创建对象的函数,如果一个函数使用 new 关键字调用,那么这个函数就是构造函数;

2.1 内置构造函数方法

JS 中是存在一个专门创建普通对象的内置函数:Object

代码样例:

// 常规添加
let obj1 = new Object();
// 添加属性
obj1.uname = '小柴';
obj1.age = 24;
// 添加方法
obj1.love = function () {
 	console.log('更文');
};
console.log( obj1 );
// 一次性添加
let obj2 = new Object( {uname : '小柴', age : 24, sex : '男'} );
console.log( obj2 );

总结:

  1. 使用 new 关键字调用函数的行为被称为实例化;
  2. 实例化构造函数时没有参数时可以省略 ()
  3. 构造函数的返回值即为新创建的对象
  4. 构造函数内部的 return 返回的值无效;

⭐注意:

  1. Object创建的对象中,其成员是无序的
  2. 实践中为了从视觉上区分构造函数和普通函数,习惯将 构造函数的首字母大写

2.2 自定义构造函数方法

为了方便解决内置构造函数在使用方式上的局限性,从而开发并兼容了自定义构造函数的方法,但是这与普通函数不同的是:所有自定义构造函数的首字母全大写

代码样式:

// 创建自定义构造函数
function Person (uname, age, sex) {
    // 设置属性
	this.uname = uname;
	this.age = age;
	this.sex = sex;
    // 设置方法
	this.eat = function () {
		console.log('吃饭');
	};
}

// 实例化对象
let o = new Person('小柴', 24, '男');
console.log( o );

⭐注意:构造函数通常以某一类的名称来命名;譬如,对象是某位博主,那么构造函数就以Person命名;

2.3 实例对象与构造函数对象匹配检测

这里的检测机制需要用到一个运算符:instanceof,其专门用于判断一个对象是否匹配另外一个构造函数的实例对象;再使用constructor 方法,指回构造函数本身;

代码样式:

// 构造函数对象
function A () {}
function B () {}
//实例化对象
let obj1 = new A();
let obj2 = new B();

// 匹配检测
console.log(obj2 instanceof A);// false
console.log(obj2 instanceof B);// true
console.log(obj1 instanceof A);// true
console.log(obj1 instanceof B);// false

//constructor:用于直接返回构造函数本身
console.log( obj1.constructor );

⭐注意:构造函数是用于实例化创建对象,那么new的执行步骤(涉及到了异步的过程)是:

  1. 在内存中开辟新空间;
  2. this指向该实例化对象;
  3. 执行构造函数里面的代码;
  4. 返回该对象;

3. 实例成员

基础概念: 通过构造函数创建的对象称为实例对象,实例对象中的属性和方法称为实例成员

代码样例:

// 构造函数
function Person() {
  // 构造函数内部的 this 就是实例对象
  // 实例对象中动态添加属性
  this.name = '小柴';
  // 实例对象动态添加方法
  this.sayHi = function () {
    console.log('大家好~');
  }
}

// 实例化,p1 是实例对象
// p1 实际就是 构造函数内部的 this
let p1 = new Person();

console.log(p1);// 访问对象
console.log(p1.name); // 访问实例属性
p1.sayHi(); // 调用实例方法

总结:

  1. 构造函数内部 this 实际上就是实例对象,为其 动态添加的属性方法 即为 实例成员
  2. 为构造函数传入不同参数,即可动态的创建结构相同但值不同的对象;
  3. 实例成员在 构造函数内部,包括实例属性和实例方法;
  4. 实例成员只能由实例对象访问;

⭐注意:构造函数创建的实例对象彼此独立互不影响

4. 静态成员

基础概念:JavaScript底层函数本质上也是对象类型 ,因此允许直接为函数动态添加属性或方法,构造函数的属性和方法被称为 静态成员

代码样例:

// 构造函数
function Person(name, age) {
    // 省略实例成员
}
// 静态属性
Person.eyes = 2;
Person.arms = 2;
// 静态方法
Person.walk = function () {
  console.log('^_^人都会走路...');
  // this 指向 Person
  console.log(this.eyes);
}

总结:

  1. 静态成员指的是添加到构造函数本身的属性和方法;
  2. 一般公共特征的属性或方法,会被设置为静态成员;
  3. 静态成员方法中的 this 指向构造函数本身;
  4. 静态成员往往是在构造函数身上直接添加的成员,包括静态属性和静态方法;
  5. 静态成员只能由构造函数访问;

三、引用类型

在在 JavaScript 中最主要的数据类型有 6 种,分别是字符串数值布尔undefinednull对象常见的对象类型数据包括数组和普通对象。其中字符串数值布尔undefinednull 也被称为 简单类型 (基础类型),对象也被称为 引用类型

它们的主要区在于数据传递方面:

那么什么是数据传递呢?其实可以简单理解为:某变量的值或内容传递给另外一个变量,称为数据传递

这里分为两种:

  1. 值传递:会把数据复制一份完成传递,也是简单类型的数据传递方式
  2. 引用传递:会把数据地址复制一份完成传递,也是引用类型的数据传递方式

JavaScript 内置了一些构造函数,绝大部的数据处理都是基于这些构造函数实现的,甚至字符串、数值、布尔、数组、普通对象也都有专门的构造函数,用于创建对应类型的数据;

不过,这里主要介绍的还是 引用类型

1. Object对象

基础概念: Object 是内置的构造函数,用于创建普通对象;

代码样例:

// 通过构造函数创建普通对象
let user = new Object({name: '小柴', age: 24});
  
// 对象语法简写
let name = '爱程序';
let people = {
  // 相当于 name: name
  name,
  // 相当于 walk: function () {}
  walk () {
     console.log('人都要走路...');
  }
}

普通对象数据保存在堆内存之中,栈内存中保存了普通对象在堆内存的地址;下图展示了普通对象在内存中的存储方式:

Web前端系列技术之JavaScript进阶(从ES6开始)②_第1张图片

普通对象在赋值时只是复制了栈内中的地址,而非堆内存中的数据,如下图所示:

Web前端系列技术之JavaScript进阶(从ES6开始)②_第2张图片
总结:

  1. 推荐使用字面量方式声明对象,而不是 Object 构造函数;
  2. 普通对象赋值后,无论修改哪个变量另一个对象的数据值也会相当发生改变;
  3. Object.assign 静态方法创建新的对象;
  4. Object.keys 静态方法获取对象中所有属性;
  5. Object.values 表态方法获取对象中所有属性值;

⭐注意:这里涉及到了栈与堆的区别

  1. 是内存中的数据存储空间;
  2. 简单类型 的数据保存在内存的 空间中;
  3. 引用类型 的数据保存在内存的 空间中, 内存中存取的是 引用类型的地址(房间号);

2. Array数组

基础概念: Array是内置的构造函数,用于创建数组;

代码样例:

// 构造函数创建数组
let arr = new Array(5, 7, 8);

数组在内存中的存储方式与普通对象一样,如下图所示:

Web前端系列技术之JavaScript进阶(从ES6开始)②_第3张图片

数组在赋值时只是复制了栈内中的地址,而非堆内存中的数据,如下图所示:

Web前端系列技术之JavaScript进阶(从ES6开始)②_第4张图片

总结:

  1. 推荐使用字面量方式声明数组,而不是 Array 构造函数;
  2. 数组赋值后,无论修改哪个变量另一个对象的数据值也会相当发生改变;
  3. 实例方法 forEach 用于遍历数组,替代 for 循环(三个参数【元素本身】、【索引值】、【数组本身】);
  4. 实例方法 filter 过滤数组单元值,生成新数组;
  5. 实例方法 map 遍历数组让每个元素执行一边回调函数,把所有结果放到新数组返回;
  6. 实例方法 join 数组单元素拼接成了符串;
  7. 实例方法 concat 合并两个数组,生成新数组;
  8. 实例方法 sort 对原数组单元值排序;
  9. 实例方法 splice 删除或替换原数组单元;
  10. 实例方法 forEach 用于遍历数组,替换for循环;
  11. 实例方法 indexOf 检索数组某元素首次出现索引值(否则返回-1);
  12. 实例方法 find 用于查找首次出现的满足条件的值(返回该值);
  13. 实例方法 lastindexOf 检索数组某元素尾次出现索引值(否则返回-1);
  14. 实例方法 findIndex 用于查找首次出现的满足条件的值(返回该索引值)
  15. 实例方法 reverse 反转数组;
  16. 实例方法 some 用于查找如果有一个满足条件(返回布尔值);
  17. 实例方法 every 用于查找如果有多个满足条件(返回布尔值);
  18. 静态方法 from 伪数组转成数组;
  19. 静态方法Array.isArray()判断一个值是否是数组;

⭐注意:

  1. 任何一个数组都是Array构造函数的实例化对象
  2. 具体的数组方法可以访问MDN官网查询:MDN数组方法文档
  3. 排序代码:
    正序排列:let 变量名 = 数组名.sort(function (a, b) {return a - b;});
    倒序排列:let 变量名 = 数组名.sort(function (a, b) {return b - a;});

3. RegExp正则

基础概念: RegExp内置的构造函数,用于创建正则表达式;

代码样例:

// 构造函数创建正则方法一:
let reg = new RegExp(/\d/);

// 构造函数创建正则方法二:
// 如果使用引号定义正则时,\d、\s、\w,需要多添加一个 \
 let reg1 = new RegExp('\\d');

// 字面量方式创建正则
let reg = /(\d)/i;

总结:

  1. 推荐使用字面量定义正则表达式,而不是 RegExp 构造函数;
  2. RegExp 静态属性 $1、$2、$3、… 获取正则分组单元;

⭐注意:任何一个正则也是一个对象;


总结

今天是学习 ES6 的第二天,内容还是挺多的,使用练习和理解极为重要,今天所总结出来的所有知识,希望对大家有用,同时也希望这篇文章可以有一个好的展现量和得到更多人的支持,谢谢每一位浏览文章的人,要相信小柴码文,必是好文,欢迎各位 点赞+收藏+关注 啦! ! !


有兴趣的小伙伴们可以回顾之前所学习的Web APIs基础学习的内容,后续即将更新前端开发的学习目标。感谢关注和支持,让我们一起成长!

有兴趣可回顾一下JavaScript基础学习的文章内容,再结合之前所介绍的CSS基础学习以及HTML基础学习,大脑里的内容会更加丰富而充实的,毕竟综合性复习和学习是更会加深印象的哟!!!

你可能感兴趣的:(ES6基础学习,前端,javascript,es6,开发语言,编程思想)