ES2020の新機能

トップ > アラカルト > ES2020の新機能

目次

ES2020とは

JavaScript の標準仕様 ES2020 (ECMAScript 11th Edision) として 2020年6月にリリースされました。ES2020 で新たに追加された機能について説明していきます。

任意精度整数(BigInt)

これまでの JavaScript では、2^53 の精度の整数しか扱うことができませんでしたが、任意の精度を持つ整数 BigInt がサポートされました。数字を BigInt 整数として表現するには数字の末尾に n をつけます。

var num1 = 123n;

通常の整数では17桁あたりから丸め誤差が出始めますが、BigInt 整数は何桁であっても誤差が生じることはありません。

console.log(1234567890123456789);	// => 1234567890123456800 ... 末尾に誤差が出ることがある
console.log(1234567890123456789n);	// => 1234567890123456789n ... 誤差は生じない

通常の整数を BigInt 整数に変換するには BigInt() を用います。

var num1 = 123;			// 通常精度の整数
var num2 = BigInt(num1);	// BigInt整数

typeof の値は bigint となります。

console.log(typeof(123n));	// => bigint

for-in ループにおける順序保証

オブジェクトの属性等を for-in ループで参照する際、これまでは順序が保障されませんでしたが、ES2020 では順序が保障されるようになりました。下記の例では、処理系によっては順不同で表示される可能性がありましたが、ES2020 では a, b, c, d, e の順に表示されることが保障されます。

var data = {a:"A", b:"B", c:"C", d:"D", e:"E"};
for (var d in data) {
    console.log(d);		// => a, b, c, d, e
}

ヌル合体(Nullish Coalescing)演算子(??)

ヌル合体(Nullish Coalescing)演算子 ?? を用いることで、値が undefinednull の時にデフォルト値を設定するといった処理を、下記の様に記述することが可能となります。

// 古い書き方(obj.fooが未設定の場合デフォルト値60を設定する)
if (typeof(obj.foo) == "undefined" || obj.foo == null) {
    obj.foo = 60;
}

// ES2020以降の新しい書き方
obj.foo = obj.foo ?? 60;

オプショナル連結(Optional Chaining)(?)

これまで、obj.foo.baa などの参照で、foo が未定義の場合 TypeError が発生していましたが、オプショナル連結 ? を用いることで、foo が未定義の場合は TypeError ではなく undefined を返却させることが可能となりました。

// 古い書き方(obj.fooが定義されていたら参照する)
if (obj.foo) {
    console.log(obj.foo.baa);
}

// ES2020以降の新しい書き方
console.log(obj.foo?.baa);	// => foo が未定義の場合は undefined

globalThis

ブラウザで動作する JavaScript でも、サーバ上で動作する Node.js でも共通に参照できるグローバルオブジェクトとして globalThis がサポートされました。ブラウザで動作する JavaScript では window オブジェクト、Node.js では global オブジェクトと同値になります。

console.log(globalThis);	// => Window {window:...}

string.matchAll()

string.matchAll(regexp) は、string の中から regexp にマッチするものをリスト(正確にはイテレーター)として返却します。

for (var m of "2020-12-31".matchAll(/[0-9]+/g)) {
  console.log(m);
}
// => ["2020", index: 0, input: "2020-12-31", groups: undefined]
// => ["12", index: 5, input: "2020-12-31", groups: undefined]
// => ["31", index: 8, input: "2020-12-31", groups: undefined]

ダイナミックインポート(Dynamic Import)

モジュールを非同期に読み込むことが可能となりました。import() は Promise を返却します。非同期にモジュールを読み込み、読み込みが完了した時点でコールバック関数を実行することができます。

import("./module.js").then(mod => {
   console.log(mod.a1);
});

export * as name from module 構文

インポートしたものを直接エクスポートすることが可能となりました。

// 以前の古い書き方
import * as mod from "./module.js";
export { mod };

// ES2020以降の新しい書き方
export * as mod from "./module.js";

import.meta

import.meta がサポートされました。現在のモジュールに関する URL などのメタ情報を得ることができます。

console.log(import.meta);
// => {url, "http://www.example.com/example.js"}

Promise.allSettled()

Promise.all() では、指定したタスクのいずれか一つがエラーになるとそこで待ち合わせを完了してしまいますが、新しくサポートされた Promise.allSettled() を用いると、タスクがエラーとなっても、すべてのタスクが成功終了するか、エラー終了するまで、処理を待ち合わせることが可能となります。

p1 = Promise.resolve("OK1");
p2 = Promise.reject("NG2");
p3 = Promise.resolve("OK3");
Promise.allSettled([p1, p2, p3]).then(
   resolveList => resolveList.forEach(res => console.log(res)),
   rejectList  => rejectList.forEach(rej => console.log(rej))
);
// => {status: "fulfilled", value: "OK1"}
// => {status: "rejected", reason: "NG2"}
// => {status: "fulfilled", value: "OK3"}

Copyright (C) 2020 杜甫々
初版:2020年12月27日、最終更新:2020年12月27日
http://www.tohoho-web.com/ex/es2020.html