본문 바로가기

Language/JavaScript

<ES9> ES2018 Features

 

1. 소개

 - ES9라도고 불리는 ES2018은 2018년에 소개된 ECMA Script의 2018버전이다.

 

 - 2015만큼은 아니지만 꽤 유용한 기능들이 추가되었다. 객체에서도 나머지 연산자와 스프레드 연산자를 사용할 수 있게 되었고, 비동기 반복이 편리해졌다.

 

2. 기능

* Spread Properties

const obj = { x: 11, y: 22, z: 33 };
const foo = { a: 9999, ...obj };
console.log(foo);
// { a: 9999, x: 11, y: 22, z: 33 }

 

 - 기존에 배열에서만 사용되었던 스프레드연산자가 객체에서도 사용가능하게 되었다.

 

 - 위를 통해 편리하게 얕은복사가 가능해졌다.

 

* Rest Properties

const obj = { x: 11, y: 22, z: 33 };
const { x, ...args } = obj;
console.log(x); // 11
console.log(args); // {y: 22, z: 33}

 

 - 객체 분해 할당 시에 분해 연산자를 이용하여 사용되지 않은 프로퍼티들을 묶을 수 있게 되었다.

 

* Promise finally

Promise.resolve()
  .then(() => {
    console.log("then 01");
  })
  .finally(() => {
    console.log("finally 01");
    throw new Error();
  })
  .then(() => {
    console.log("then 02");
  })
  .catch(() => {
    console.log("catch 01");
  })
  .finally(() => {
    console.log("finally 02");
  });
//   then 01
//   finally 01
//   catch 01
//   finally 02

 

 - 프라미스에 finally 키워드가 추가되었다. 이는 이행될때 시행되는 then과 거절될 때 시행되는 catch 와는 전혀다른 성격을 갖고 있다. finally는 반드시 실행되는 키워드이다.

 

 - 만일 finally 안에서 예외가 발생하면 rejected 상태로 변화하고 아래의 catch가 실행된다. 위의 코드에서 첫 번째 finally 다음의 then이 실행되지 않는 것이 바로 그 이유이다.

 

* for await of

const delay = (time) => new Promise((resolve, reject) => setTimeout(() => resolve(time), time));

async function asyncFunc() {
  const promises = [delay(1000), delay(1000), delay(1000)];
  for await (const p of promises) {
    console.log(p);
  }
}

asyncFunc();

 

 - for await of 로 주어진 iterator 에 프로미스가 포함된 경우를 처리할 수 있게 되었다. 위를 실행하면 1초뒤에 세 개의 1000이 출력된다.

 

 - ES2018 이전에는 아래와 같이 처리했다.

 

const delay = (time) => new Promise((resolve, reject) => setTimeout(() => resolve(time), time));

async function asyncFunc() {
  const promises = [delay(1000), delay(1000), delay(1000)];
  for (const p of promises) {
    const data = await p;
    console.log(data);
  }
}

asyncFunc();

 

* Symbol asynciterator

- 이번에는 위와 달리 ES2018 이전에 비동기 이터레이터를 사용한 예제를 먼저 보자.

 

const delay = (time) => new Promise((resolve, reject) => setTimeout(() => resolve(time), time));

const myIterator = {
  *[Symbol.iterator]() {
    for (let _ = 0; _ < 5; _++) {
      yield delay(1000);
    }
  },
};

async function myFunc() {
  for (const p of myIterator) {
    const value = await p;
    console.log(value);
  }
}

myFunc();

 

 - 참고로 제너레이터는 이터러블이므로 반복이 가능하다. 이를 통해 이터레이터 객체를 생성하여 반복문을 시행하였다.

 

 - 프라미스이므로 async await 을 사용하기 위해 await 를 사용하여 value 에 할당후 console을 찍었다. 이를 for await of 로 만들 수 있을까. 이 때 사용되는 것이 Symbol.asyncIterator 이다.

 

const delay = (time) => new Promise((resolve, reject) => setTimeout(() => resolve(time), time));

const myIterator = {
  async *[Symbol.asyncIterator]() {
    for (let _ = 0; _ < 5; _++) {
      yield await delay(1000);
    }
  }
};

async function myFunc() {
  for await (const p of myIterator) {
    console.log(p);
  }
}

myFunc();

 

- asyncIterator 는 iterator와 달리 async await 키워드를 사용할 수 있다.

 

 - asyncIterator로 구현된 이터레이터 객체는 for awiat of 를 사용할 수 있다. 만일 객체내에 Symbol.iterator 와 Symbol.asyncIterator가 동시에 구현된 경우 각각 for-of , for-await-of 시 선택된다.

 

 

 - 위의 기능들 외에도 정규표현식에 몇가지 기능이 추가되었다. 그중 대표적으로 Named Capture Groups와 Unicode Property Escapes가 추가되었다.

 

 - 정규식에서 캡쳐 그룹이 문자열 이름을 가질 수 있게 되었고, 자주 사용되는 유니코드 패턴을 제공한다. \p{Emoji}/ 와 같이 유니코드셋 카테고리명을 적어서 패턴을 사용한다. 카테고리 종류는 MDN에서 확인할 수 있다.

 

 


 

참고

 

 

JavaScript ES2018 Features With Examples

ES2018 a.k.a. ES9 features

betterprogramming.pub

 

 

New ES2018 Features Every JavaScript Developer Should Know

The ninth edition of the ECMAScript standard, officially known as ECMAScript 2018 (or ES2018 for short), was released in June 2018. Starting with ES2016,

css-tricks.com

 

 

ES9 (ES2018) New Features - 변경점 총정리

ES9 는 정규식과 비동기 작업에 대한 새로운 기능이 주요 변경점입니다. 기존의 Iterator 와 이번에 나온 Async Iterator 와의 차이점을 숙지해야 합니다. 톺아보기 : Async Promise.prototype.finally() Async It..

aerocode.net

 

 

제너레이터

 

ko.javascript.info