ホームページ > 記事 > ウェブフロントエンド > vue で使用される es6 の機能は何ですか?
#このチュートリアルの動作環境: Windows7 システム、vue3 バージョン、DELL G3 コンピューター。特徴: 1. Let および const キーワードは変数の宣言に使用されます; 2. "for...of" ループ、反復可能なデータ; 3. Iterable、反復可能なプロトコルを実装するオブジェクト; 4.ジェネレータ ; 5. デフォルトパラメータ; 6. オブジェクト/配列から属性/値を削除できる代入構文の構造化; 7. 残り/拡張されたパラメータ; 8. アロー関数; 9. オブジェクトリテラル; 10. クラス; 11. マップ/ Set/WeakMap/WeakSet データ構造; 12. お約束。
ブロック スコープ、クラス、アロー関数、ジェネレーター、その他多くの便利な機能などの強力な機能が付属しています。
プログラミング エクスペリエンスを向上させ、開発効率とコード品質を向上させるために、Vue アプリケーション開発で使用されるすべての必要な関数。Vue CLI の
Babel または
core-js 統合を通じて、開発中のコードを構成仕様に厳密に従って反復できるため、チームにとって役立ちますコラボレーション。この記事では、Vue アプリケーション開発で一般的に使用されるいくつかの ES6 機能を紹介します。
let と
const。
let は
var に似ていますが、
let を使用して宣言された変数のスコープは、変数が宣言されているブロック内になります。 (ブロックとは、条件ブロック、
for ループ ブロックなどを指します。)
let を使用すると、ブロック内の変数のスコープが設定され、ブロック外では利用できません。
if (true) { let foo = "word"; } console.log(foo); // errorここで、エラーは生産プロセス中に発生する可能性のあるエラーを防ぐため、良いものです。 上記の例で (従来の Javascript コードで行うように)
let の代わりに
var を使用すると、エラーは発生しません。
const は、変数を宣言するために使用されるもう 1 つの ES6 キーワードです。違いは、
const で作成された変数は宣言後に変更できないことです。この機能により、
BUG の発生を効果的に回避できます。そのため、コードを記述するときは、純粋な関数を次のように記述することをお勧めします。可能な限り (純粋な関数とは、関数への固定入力が与えられると、出力結果が固定され、関数外の変数などの影響を受けないことを意味します)。
const a = 2021 a = 2020 // error変数を作成するにはいくつかの方法がありますが、どれを使用すればよいですか?最良の方法は、可能な限り
const## を使用することです。 #。 let
は、for
ループなど、後で変更する必要がある変数が必要な場合にのみ使用してください。
for ループを記述する簡単な方法があります。
。 たとえば、従来の
ループは次のようになります: <pre class="brush:js;toolbar:false;">const arr = [1, 2, 3];
for (let i = 0; i < arr.length; i++) {
const item = arr[i];
console.log(item);
}</pre>
ES6 では、非常に単純です:
const arr = [1, 2, 3]; for (const item of arr) { console.log(item); }
## は使用しないでください。 #for ..in
構文の混乱; これらはまったく別のものです。for..in は配列/オブジェクト内のプロパティを取得し、
for..of は反復処理する実際のデータを取得します。
Iterable
iterable
プロトコルを実装するオブジェクトは次のとおりです:const twice = { [Symbol.iterator]() { let i = 0; const iterator = { next() { if (i < 2) { return { value: i++, done: false }; } else { return { value: undefined, done: true }; } }, }; return iterator; }, };
これで、この ## を
for..of## で使用できるようになります。 # ループ #twiceObject: for(const x of twice){ console.log(x) }
これは、
twice オブジェクトを 2 回ループし、それぞれ
0 と 1 を取得します。
反復可能オブジェクトを作成するために、
iterable プロトコルと
iterator
反復可能オブジェクトであるという要件を満たすには、
[Symbol.iterator] という名前のメソッドが必要です。
const twice = { [Symbol.iterator]() { ... } }2 つの新しい ES6 トリックがメソッド名に適用されています。
まず、
Symbol.iterator
Symbol
は ES6 で一意のタグ/識別子を作成するために使用される基本型です。2 番目に、プロパティ キーを角かっこで囲むことで、動的に計算されるキーになります。ここで重要なのは式の表記です。イテレータは次のように評価されますが、通常は実際の評価が何であるかは関係ありません。この重要でない詳細は抽象化されています。
これは反復可能なプロトコルです。イテレータは
[Symbol.iterator]
value と
done
next メソッドを持つオブジェクトだけです。反復を停止したい場合は、オブジェクト
{値: 未定義、完了: true} を返すだけです。
これは例の反復子です:
const iterator = { next() { if (i < 2) { return { value: i++, done: false }; } else { return { value: undefined, done: true }; } }, };
つまり、反復可能プロトコルと反復子プロトコルの両方を満たすオブジェクトが存在します。次のコードのような:
const twice = { [Symbol.iterator]() { let i = 0; const iterator = { next() { if (i < 2) { return { value: i++, done: false }; } else { return { value: undefined, done: true }; } }, }; return iterator; }, };
数组和字符串可以使用
for..of
,进行迭代。这意味着这些内置类型包含与上面的类似的[Symbol.iterator]
方法。
与迭代相关的另一个功能是生成器。
上面的可迭代代码依靠闭包来存储 i
变量。使用 generator
时,不必担心自己构造闭包:
function* twiceGen() { let i = 0; while (i < 2) { yield i; i++; } } const twice = twiceGen();
该代码实现了与可迭代示例相同的行为,但更为简单。
可以与for..of
完全相同地使用它:
for(const item of twice){ console.log(item) }
如你所见,它是一个带有星号(*
)声明的函数。它使用yield
关键字逐个抽取值,就像迭代器的next
方法一样。
生成器是一种多功能工具,基本上,它是一种允许暂停/恢复功能的机制。不必在for..of
中使用上述twice
对象。可以调用它的next
方法。
function* twiceGen() { const i = 0; while (i < 2) { yield i; } } const twice = twiceGen(); twice.next().value; // 0
此时,twiceGen
函数在第一次运行while
循环后暂停。如果再次运行相同的操作,它将恢复并播放循环的第二次运行。
twice.next().value; // 1
生成器的妙处在于它还创建了一个可迭代的迭代器对象。这就是为什么我们能够使用for..of
(可迭代特权)迭代两次并直接调用其next
方法(迭代器特权)的原因。
可能不会立即创建自己的迭代器、生成器,所以让我们来看看其他一些ES6的独创性,它们可以立即使你的代码更加友好。
就像许多其他编程语言一样,现在可以为函数参数设置默认值。
过去是这样实现默认值的:
function addOne(num) { if (num === undefined) { num = 0; } return num + 1; } addOne();
现在可以这样:
function addOne(num = 0) { return num + 1; } addOne();
解构赋值语法是一种 Javascript 表达式。通过解构赋值, 可以将属性/值从对象/数组中取出,赋值给其他变量。
如果要将对象传递给函数,则可以轻松选择对象的属性,然后使用ES6分解语法将它们放在单独的变量中:
function foo({ a, b }) { console.log(a, b); // 1, 2 } foo({ a: 1, b: 2 });
这种解构语法的好处是可以避免创建带有附加代码行的变量。因此不需要像下面这样:
function foo(obj) { const a = obj.a; const b = obj.b; console.log(a, b); // 1, 2 }
同样,还可以在解构语法中设置默认值:
function foo({ a = 0, b }) { console.log(a, b); // 0, 2 } foo({ b: 2 });
解构语法也适用于赋值:
function foo(obj) { const { a, b } = obj; console.log(a, b); // 1, 2 }
当从参数以外的地方获取对象时,这也很有用。
function getObj() { return { a: 1, b: 2 }; } function foo() { const { a, b } = getObj(); console.log(a, b); // 1, 2 }
解构技巧同样也适用数组。
解构参数:
function foo([a, b]) { console.log(a, b); // 1, 2 } foo([1, 2, 3]);
解构赋值:
function foo(arr) { const [a, b] = arr; console.log(a, b); // 1, 2 }
在解构数组时,可以使用 ...
语法来获取数组中的所有其他项。
function foo([a, b, ...c]) { console.log(c); // [3, 4, 5] } foo([1, 2, 3, 4, 5]);
c
现在是一个包含自己的数组,包含了其余的元素:3
,4
,5
。这里的操作就是Rest
操作。
这个语法同样适用于赋值:
function foo(arr) { const [a, b, ...c] = arr; console.log(c); // [3, 4, 5] } foo([1, 2, 3, 4, 5]);
rest
操作符也可以单独使用,无需解构:
function foo(...nums) { console.log(nums); // [1, 2, 3, 4, 5] } foo(1, 2, 3, 4, 5);
在这里,我们将数字作为独立参数传递,而不是作为单个数组传递。但是在函数内部,使用rest
运算符将数字作为单个数组收集。当遍历这些参数时,这很有用。
rest语法 ...
与另一个ES6特性操作符扩展完全相同。
例如,如果要将两个数组合并为一个:
const a = [1, 2]; const b = [3, 4]; const c = [...a, ...b]; console.log(c); // [1, 2, 3, 4]
spread
操作符用于将所有项展开,并将它们放入不同的数组中。
spread
也适用于对象:
const obj = { a: 1, b: 2 }; const obj2 = { ...obj, c: 3 }; console.log(obj2); // { a: 1, b: 2, c: 3 }
现在,第二个对象除了其自身的属性外,还应包含第一个对象的所有内容。
ES6提供了创建函数,对象和类的更简单方法。
箭头函数表达式的语法比函数表达式更简洁,并且没有自己的this
,arguments
,super
或new.target
。箭头函数表达式更适用于那些本来需要匿名函数的地方,并且它不能用作构造函数。
使用箭头语法来创建更简洁的函数:
const addOne = (num) => { return num + 1; };
箭头语法对于创建单行函数更加简洁友好。
const addOne = (num) => num + 1;
此函数将自动返回表达式num +1
的求值作为返回值,不需要显式的使用return
关键字。
如果函数仅接受一个参数,甚至可以省略括号(但是在严格语法上还是建议加上括号):
const addOne = num => num + 1;
但是如果没有任何参数,仍然需要一对空括号:
const getNum = () => 1;
但是,此语法有一个警告,如果我们返回的是对象字面量,则无法使用,会报错:
const getObj = () => { a: 1, b: 2 } // error
这将产生语法错误,因为解析器将假定花括号用于函数块,而不是对象字面量。
为了避免这个错误,必须将对象字面量包装在一对括号中:
const getObj = () => ({ a: 1, b: 2 });
另一件需要记住的事情是,this
关键字不能在箭头函数中使用。它不会出现错误;相反,它只会从周围的范围提供相同的this
引用。
function thatOrThis() { const that = this; const compare = () => { console.log(that === this); // true }; compare(); } thatOrThis();
以上代码给出的值则为:true
ES6也提供了一种更简单的方法来创建对象字面量。
如果在一个对象中放入两个项目,它们的属性键与变量相同,可以用传统的Javascript做这样的事情:
const a = 1; const b = 2; const obj = { a: a, b: b, };
但是在ES6中,语法可以更简单:
const a = 1;const b = 2;const obj = { a, b };
如果把方法放到对象字面量中,可以这样做:
const a = 1; const b = 2; const obj = { a, b, getA() { return this.a; }, getB() { return this.b; }, };
基本上,没有
function
关键字和冒号。
ES6提供了类似于其他面向对象语言的类构造。现在不必依赖于混淆构造函数和原型方式。
class Person { constructor(name, hobby) { this.name = name; this.hobby = hobby; } introduce() { console.log(`大家好,我的名字叫:${this.name},我喜欢${this.hobby}。`); } } const devpoint = new Person("DevPoint", "coding"); devpoint.introduce();
附带说明,introduce
方法中的字符串称为模板字符串,它是使用反引号而不是引号创建的。这样可以使用美元符号和大括号将表达式插入字符串。
与常规字符串拼接相比,模板字符串的好处是它可以跨越多行:
const str = `line 1 line 2 line 3 `; console.log(str);
它被称为模板字符串,因为它对实现模板很有用。
function pStr(text) { return `<p>${text}</p>`; } pStr("Hello world"); // <p>Hello world</p>
一个类可以从另一个类继承(重用现有类的代码):
class Person { constructor(name, hobby) { this.name = name; this.hobby = hobby; } introduce() { console.log(`大家好,我的名字叫:${this.name},我喜欢${this.hobby}。`); } } class ProfessionalPerson extends Person { constructor(name, hobby, profession) { super(name, hobby); // 执行 Person 的构造函数 this.profession = profession; } introduce() { super.introduce(); // 调用 Person 类的方法 console.log(`我的职业是 ${this.profession}。`); } } const devpoint = new ProfessionalPerson("DevPoint", "coding", "程序员"); devpoint.introduce();
这里使用extends
关键字在两个类之间创建继承关系,其中Person
为父类。代码中用了两次super
关键字,第一次是在构造函数中调用父类的构造函数,第二次,像使用对象一样使用它来调用父类的introduce
方法。super
关键字的行为会因使用的位置而异。
在构造函数中使用时,
super
关键字将单独出现,并且必须在使用this
关键字之前使用。如下代码就是有异常的。
class ProfessionalPerson extends Person { constructor(name, hobby, profession) { this.profession = profession; // 这里会出现异常 super(name, hobby); // 执行 Person 的构造函数 } introduce() { super.introduce(); // 调用 Person 类的方法 console.log(`我的职业是 ${this.profession}。`); } }
ES6新增了两种数据结构:Map
和Set
Map
是键-值
对的集合,并且能够记住键的原始插入顺序。
const mapPerson = new Map(); mapPerson.set("name", "DevPoint"); mapPerson.set("profession", "Coding"); const myName = mapPerson.get("name"); console.log(myName); // DevPoint
Map
对象可以使用任何对象类型作为键。看起来是不有点像Object,下面我们可以看看他们的比较:
Map | Object | |
---|---|---|
意外的键 |
Map 默认情况不包含任何键,只包含显式插入的键。 |
一个 Object 有一个原型,原型链上的键名有可能和你自己在对象上的设置的键名产生冲突。 |
键的类型 |
Map 的键可以是任意值,包括函数、对象或任意基本类型。 |
一个 Object 的键必须是一个 String 或是 Symbol 。 |
键的顺序 | Map 中的 key 是有序的。因此,当迭代的时候,一个 Map 对象以插入的顺序返回键值。 |
一个 Object 的键是无序的 |
Size |
Map 的键值对个数可以轻易地通过 size 属性获取 |
Object 的键值对个数只能手动计算,需要自己构建方法 |
迭代 | Map 是 iterable 的,所以可以直接被迭代。 |
迭代一个 Object 需要以某种方式获取它的键然后才能迭代。 |
性能 | 在频繁增删键值对的场景下表现更好 | 在频繁添加和删除键值对的场景下未作出优化 |
Set
对象就像一个数组,但是仅包含唯一项。Set
对象是值的集合,可以按照插入的顺序迭代它的元素。 Set
中的元素只会出现一次,即 Set
中的元素是唯一的。
const numbers = new Set(); numbers.add(1); numbers.add(1); console.log(numbers); // Set { 1 }
尽管两次add
是同样的值,程序本身不会出现任何异常,但该集合仍然只包含一项。
让谈谈来学习一点更复杂的知识,WeakMap
和WeakSet
。它们分别是Map
和Set
的弱引用版本。
WeakMap
其键必须是Object
,而值可以是任意的。
WeakSet
对象是一些对象值的集合, 并且其中的每个对象值都只能出现一次,在WeakSet
的集合中是唯一的。
它和 Set
对象的区别有两点:
Set
相比,WeakSet
只能是对象的集合,而不能是任何类型的任意值。WeakSet
持弱引用:集合中对象的引用为弱引用。 如果没有其他的对WeakSet
中对象的引用,那么这些对象会被当成垃圾回收掉。 这也意味着WeakSet
中没有存储当前对象的列表。 正因为这样,WeakSet
是不可枚举的。一旦不再引用WeakMap
的键,便会对其进行垃圾回收(由Javascript运行时从内存中删除)。
let key1 = {}; const key2 = {}; const wm = new WeakMap(); wm.set(key1, 1); wm.set(key2, 2); key1 = null; // 取消引用
在key1
被取消引用之后,它的对应值将被垃圾回收,意味着它将在未来的某个时间点消失。
同样,如果将一个对象添加到WeakSet
中,然后再取消引用它,它也将被垃圾回收。
let item1 = {}; const item2 = {}; const ws = new WeakSet(); ws.add(item1); ws.add(item2); item1 = null; // 取消引用
Promise
对象用于表示一个异步操作的最终完成 (或失败)及其结果值。是ES6的一个常用功能,它是对传统函数回调模式的改进。
一个 Promise 必然处于以下几种状态之一:
pending
): 初始状态,既没有被兑现,也没有被拒绝。fulfilled
): 意味着操作成功完成。rejected
): 意味着操作失败。例如,这是使用传统回调的方式:
setTimeout(function () { const currentTime = new Date(); console.log(currentTime); }, 1000);
这是一个计时器,显示一秒钟后的时间。
这是一个使用相同setTimeout
逻辑的Promise
对象:
const afterOneSecond = new Promise(function (resolve, reject) { setTimeout(function () { const currentTime = new Date(); resolve(currentTime); }, 1000); });
它接受带有两个参数的函数:resolve
和reject
。这两个都是当有返回值时可以调用的函数。调用resolve
函数返回一个值,可以调用reject
函数返回一个错误。
然后,可以使用then
语法将回调函数附加到这个afteronessecond
对象上:
afterOneSecond.then((t) => console.log(t));
promise
相对于传统回调的好处是promise
对象可以被传递。因此,在设置promise
之后,可以自由地将它发送到其他地方,以处理计时器解析后要做的事情。
另一个很酷的事情是,promise可以与多个then子句链接在一起,即promise
的链式调用。
afterOneSecond.then((t) => t.getTime()) .then((time) => console.log(time));
每个
then
子句将其值作为参数返回到下一个then
子句。
下面就来介绍在VUE中,比较实用的ES6的方法或属性。
Object.assign()
方法用于将所有可枚举属性的值从一个或多个源对象分配到目标对象。它将返回目标对象。提供了一种简单的方法来浅克隆现有对象。
const obj1 = { a: 1 } const obj2 = Object.assign({}, obj1)
构造并返回一个新字符串,该字符串包含被连接在一起的指定数量的字符串的副本。
const str = "DevPoint ".repeat(3);console.log(str); // DevPoint DevPoint DevPoint
用来判断当前字符串是否以另外一个给定的子字符串开头(区分大小写),并根据判断结果返回
true
或false
。
const str = "DevPoint".startsWith("D"); const str2 = "DevPoint".startsWith("d"); console.log(str); // true console.log(str2); // false
用来判断当前字符串是否是以另外一个给定的子字符串“结尾”的,根据判断结果返回
true
或false
。
const str = "DevPoint".endsWith("t"); console.log(str); // true
用于判断一个字符串是否包含在另一个字符串中,根据情况返回
true
或false
。
const str = "DevPoint".includes("P"); console.log(str); // true
返回数组中满足提供的过滤函数的第一个元素的值,否则返回
undefined
。
const arrNumbers = [5, 12, 8, 130, 44]; const foundNumbers = arrNumbers.find((number) => number > 10); console.log(foundNumbers); // 12是数组第一个大于10的数
这不是方法而是属性,返回函数实例的名称,每个函数都有一个
name
属性,该属性提供字符串形式的函数名称
// setTimeout.name; // "setTimeout" const weather = () => { console.log("今天天气真好!"); }; const devpoint = () => {}; // 限制回到函数的名称 const enter = (callback) => { const accessName = ["weather"]; if (accessName.includes(callback.name)) { callback(); } }; enter(devpoint); enter(weather);
上述代码只执行了函数 weather
。
ES6的新特征,某种程度上代表的Javascript在未来的态度,这些新的特征让我迫不及待应用到项目中,不断接受新挑战,提升自己技能。
以上がvue で使用される es6 の機能は何ですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。