前端面试(一)ES6

本文深入探讨了模块化的发展历程,从AMD到ES6的import和export,比较了Class与传统构造函数的差异,解析了继承的实现方式,并介绍了Promise的用法,最后展示了ES6中let/const、多行字符串、解构赋值等实用功能。

模块化的使用和编译环境

没有模块化 —> AMD成为标准,require.js(也有CMD) —> 前端打包工具(如: webpack) —> ES6

语法: import、 export、 export default

环境: babel编译ES6语法, 模块化可以用webpack 和 rollup

Class与JS构造函数的区别

  • JS构造函数

function MathHandle(x, y) {
    this.x = x
    this.y = y
}
MathHandle.prototype.add = function () {
    return this.x + this.y
}
var m = new MathHandle(1, 2)
console.log(m.add())复制代码

  • Class基本语法

class MathHandle{
  constructor(x, y) {
    this.x = x    this.y = y
  }
  add () {
    return this.x + this.y
  }
}
const m = new MathHandle(1, 2)
console.log(m.add())复制代码

  • 语法糖(两种写法本质一样但是class更加简洁)

console.log(typeof MathHandle)  // 'function'
console.log(MathHandle.prototype.constructor === MathHandle)  // true
console.log(m.__proto__ === MathHandle.prototype)  // true复制代码

  • 继承

// 动物
function Animal() {
    this.eat = function () {
        alert('Animal eat')
    }
}
// 狗
function Dog() {
    this.bark = function () {
        alert('Dog bark')
    }
}
// 绑定原型,实现继承
Dog.prototype = new Animal() 
// 把低级函数的原型赋值成高级函数的实例
var hashiqi = new Dog()
hashiqi.bark()
hashiqi.eat()复制代码

//class继承:
class Animal {
  constructor(name) {
    this.name = name
  }
  eat() {
    console.log(`${this.name}eat`)
  }
}
class Dog extends Animal {
  constructor(name) {
    super(name) // 被继承的constructor
    this.name = name
  }
  say () {
    console.log(`${this.name}say`)
  }
}
const dog = new Dog('哈士奇')
dog.say()
dog.eat()
复制代码


Promise的用法(基本语法)

(1)new Promise 实例,而且要return

(2)new Promise时要传入函数,函数有resolve reject 两个参数

(3)成功时执行resolve(),失败时执行reject()

(4)then 监听执行结果

  • Callback Hell (promise的出现就是为了解决callback hell)

function loadImg(src, callback, fail) {
  var img = document.createElement('img')
  img.onload = function() {
    callback(img)
  }
  img.onerror = function() {
    fail()
  }
  img.src = src
}
var src = '图片地址'
loadImg(src, function(img) {  
// 在实际开发过程中 这里可能需要其他的很多操作
   console.log(img.width)
},function() {
  console.log('failed')
})复制代码

  • Promise 语法

function loadImg(src) {
  const promise = new Promise(function (resole, reject) {
    var img = document.createElement('img')
    img.onload = function () {
      resolve(img) // 解决
    }
    img.onerror = function () {
      reject() // 拒绝
    }
    img.src = src
  })
  return promise
}
var src = '图片地址'
var result = loadImg(src)
result.then(function (img) {
  console.log(img.width)
},function () {
  console.log(failed)
})
result.then(function (img) {
  console.log(img.height)
})复制代码

ES6其他常用功能

  • let/const
  • 多行字符串/模板变量 (反引号、${}引用变量)
  • 解构赋值

// JS
var obj = { a: 100, b: 200 }
var a = obj.a
var b = obj.b
var arr = ['XXX', 'YYY', 'ZZZ']
var x = arr[0]
// ES6
const obj = { a: 10, b: 20, c: 30 }
const {a, c} = obj
console.log(a) // 10
console.log(c) // 30
const arr = ['XXX', 'YYY', 'ZZZ']
const [x, y, z] = arr
console.log(x) 
console.log(y)
console.log(z)复制代码

  • 块级作用域

// JS
var obj = { a: 100, b: 200 }
for (var item in obj) {
  console.log(item) // a, b
}
console.log(item) // b
// ES6
const obj = { a: 10, b: 20, c: 30 }
for (let item in obj) {
  console.log(item) // a, b, c
}
console.log(item) // undefined复制代码

  • 函数默认参数

function (a=0) {} // 默认0复制代码

  • 箭头函数(this)指向(只是对普通函数的补充,this指向也指向了函数体外最近的一层的this而不是指向window变量)

function fn () {
  console.log('real', this) // {a:100}
  const arr = [1, 2, 3]
  // 普通JS
  arr.map(function(item) {
    console.log('js', this) // window
    return item + 1
  })  
// 箭头函数
  arr.map(item => {
    console.log('es6', this) // {a:100}
    return item + 1
  })
}
fn.call({a: 100})复制代码


### 前端开发 ES6 面试常见问题及答案 #### 1. **什么是ES6?为什么我们需要学习它?** ES6 是 JavaScript 的下代标准,正式名称为 ECMAScript 2015。它是对 JavaScript 核心功能的次重大升级,引入了许多新特性来简化代码编写并提高可读性和性能[^1]。通过学习 ES6,开发者可以更高效地构建复杂的 Web 应用程序,并遵循现代编程的最佳实践。 #### 2. **ES6 中有哪些重要的新增特性?** 以下是 ES6 的几个主要改进: - **模板字符串**:允许嵌入表达式和多行字符串。 - **箭头函数**:提供了种简洁的方式来定义匿名函数,同时解决了 `this` 绑定问题。 - **解构赋值**:可以从数组或对象中提取数据到变量中。 - **默认参数**:支持在函数定义时指定参数的默认值。 - **Rest 参数与 Spread 运算符**:用于处理不定数量的参数以及展开数组或对象。 - **模块化 (import/export)**:使代码组织更加清晰和易于维护。 - **Promise**:提供了更好的异步操作管理方式[^3]。 #### 3. **如何理解 let 和 const 关键字的区别?** `let` 和 `const` 是 ES6 新增的两个关键字,它们的主要作用是用来声明局部变量。相比传统的 `var`,这两个关键字具有块级作用域的特点,并且不会发生变量提升现象。具体来说: - 使用 `let` 定义的变量可以在同作用域内重新赋值;而使用 `const` 定义的常量旦初始化就不能再改变其绑定的内容(对于基本类型),或者修改指向的对象本身(对于引用类型)。另外需要注意的是,在尝试访问尚未被显式声明过的 `let` 或者 `const` 变量时会产生错误,因为这些变量处于所谓的“暂时性死区”之中[^4]。 #### 4. **谈谈 Promise 的工作原理及其优势?** Promises 提供了个更为优雅的方法去解决回调地狱的问题。每个 promise 对象代表个已完成或将要完成的操作的结果。它可以有三种状态——等待态(pending),成功态(fulfilled)或者是失败态(rejected)。当某个事件完成后,promise 将调用相应的 handler 函数(`resolve`) 来通知消费者该任务已经结束; 如果过程中出现了异常情况,则会触发另个特定处理器 (`reject`) 。无论哪种情形下,最终都会执行链式的 `.then()` 方法中的逻辑,其中第个回调接收成功的 value ,第二个则捕获任何抛出的 error 。如果没有定义后者的话,默认情况下未被捕获的 rejection 错误会自动传递给后续最近的个 catch 处理器[^5]。 ```javascript // 示例代码展示 Promises 的基础用法 function fetchData(url){ return new Promise((resolve, reject)=>{ const xhr = new XMLHttpRequest(); xhr.open('GET', url); // 创建 HTTP 请求 [^2] xhr.onload = function(){ if(xhr.status === 200){ resolve(JSON.parse(xhr.responseText)); }else{ reject(Error("Error loading data")); } }; xhr.onerror = ()=> reject(Error("Network Error")); xhr.send(); }); } fetchData('/api/data') .then(data => console.log(data)) .catch(error => console.error(error.message)); ``` #### 5. **解释下 Object.keys(), Object.values() 和 Object.entries() 的用途?** 这三个方法都是由 ES6 添加至全局对象上的静态属性,旨在帮助我们轻松遍历普通 JS Objects : - `Object.keys(obj)` 返回个包含已枚举属性名组成的数组; - `Object.values(obj)` 获取所有的值作为列表形式呈现出来; - `Object.entries(obj)` 则生成 key-value pairs 形成二维结构的数据集以便进步迭代运算. --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值