JavaScript并不是一种静态语言。是呀 JavaScript 的确不是一门静态语言,所以强调这个,这是因为 js 动态不仅体现在语言层面,语法更新比较频繁吧,甚至连版本名都变了,用年份来标记语言的版本。所以当我们提到 ES5 ,ES6 会有点 confusing,所以今天我要聊一聊的 ES7 也不确定是否和接下来要聊特性对得上,从 ES6 的发布开始(正式名称为 ES2015),javascript 一路高歌猛进,一个曾经被人视为 toy 的,引入了一个阶段性系统来标记功能和变化的进展。
今天主要聊一聊一些 ES7 的新特征
- String 的方法 padStart/padEnd
- Object.values/entries
- Object.getOwnPropertyDescriptors
- Async/Await 异步编程的支持,
padStart/padEnd
padStart(targetLength [, padString])
padEnd(targetLength [, padString])
这个在字符串新增方法,当我们指定了 targetLength 长度,如果字符长度小于指定的长度就会从padString截取一定数量字符串在该字符串前/后(padStart/padEnd)填充补位。如下
console.log('test'.padStart(6))//abcdtest
那么如何targetLength<='test'.length这两种情况(小于或等于)输出 test
console.log('test'.padStart(3))//test
如果没有指定 padString 这用空格填充补位
console.log('test'.padStart(8))
Object.values/Object.entries
该方法Object.values返回对象的属性值的数组或数组元素组成数组,接下来分别对象和数组两种形式来说明如何使用Object.values方法以及其返回值格式
const ml_tut = {title:"basic machine learning",chapters:12}
console.log(Object.values(ml_tut)) //[ 'basic machine learning', 12 ]
const ml_classic_models = ['SVM','DT','EM']
console.log(Object.values(ml_classic_models)) //[ 'SVM', 'DT', 'EM' ]
该方法Object.entries返回一个包含的属性值的数组或数组元素组成数组,不过格式[key, value]对数组。对于对象 key 为属性名而 value 为属性值,对于数组 key 为索引,而 value 为数组元素值。
const model_map = {
svm: 1,
dt: 2,
em: 3
}
console.log(Object.entries(model_map))//[ [ 'svm', 1 ], [ 'dt', 2 ], [ 'em', 3 ] ]
const ml_classic_models = ['SVM','DT','EM']
console.log(Object.entries(ml_classic_models))//[ [ '0', 'SVM' ], [ '1', 'DT' ], [ '2', 'EM' ] ]
getOwnPropertyDescriptors()
这个方法返回一个对象的所有自有的(非继承的)属性描述符。JavaScript 中的任何对象都有一组属性,每个属性都有一个描述符,描述符用于说明一个属性的一些属性,例如自读、可枚举等等。
- value: 获取属性值
- writable: true 表示该属性可以被修改
- get: 当读取属性时调用函数
- set: 为属性设置值调用
- configurable: 当为 false 时,该属性不能被删除
- enumerable: 当为 true 时,属性可以被枚举
const ml_tut = {
title: 'machine learning',
chapter: 12,
};
const descriptors = Object.getOwnPropertyDescriptors(ml_tut);
console.log(descriptors.title.value);
console.log(descriptors.chapter.writable); // true
ES6 给我们带来了Object.assign(),使用Object.assign()可以从一个或多个对象中所有可枚举的属性复制到一个对象上,然后将其返回。
然而,这有一个问题无法复制没有默认值的属性,例如一个对象只有一个 setter,那么使用 Object.assign() 就不能正确地复制到一个新的对象,听起来可能抽象,还是用代码解释一下吧,上代码
const tut = {
set title(newTitle){
console.log(newTitle)
}
}
const tut2 = {}
Object.assign(tut2, tut)
const tut3 = {}
Object.defineProperties(tut3,
Object.getOwnPropertyDescriptors(tut))
tut.title = "a new title for tut"
tut2.title = "a new title for tut2"
tut3.title = "a new title for tut3"
所以在下面输出中没有a new title for tut2
a new title for tut
a new title for tut3
Async Function
ES2017 引入了 Async Function 的概念,这是本 ECMAScript 版本中做的最重要的更改。Async Function 是 Promise 和 generator 的组合。
在 ES6 中引入了 promise,是为了解决异步代码的问题,因为 promise 出现让异步有所改善 ES6 和 ES2017 之间的两年时间里,但是 promise 还不最佳的异步编程的解决方案。而是一个临时的解决方案,本身就引入了复杂性,而且是语法上的复杂性,所以好的异步编程是让我们感觉不出自己在写异步。其实有关异编程这块想随后单拿出一个分享来做,今天我们看一看如何使用 async 和await来实现一个异步编程。
function sendMessage() {
return new Promise((resolve)=>{
setTimeout(() => resolve('I did something'), 2000)
})
}
// promise generator
async function recieveMessageAndPass() {
const something = await sendMessage()
return something + ' and I watched'
}
async function recieveMessageAndReadMessage() {
const something = await recieveMessageAndPass()
return something + ' and I watched as well'
}
recieveMessageAndReadMessage().then((res) => {
console.log(res)
})