Интересные нововведения в JavaScript ES2021
В этой статье вы узнаете про интересные нововведения в JavaScript, которые ожидают нас в 2021 году. Не все конечно, но тут собраны и описаны самые интересные из них.
Каждый год в JavaScript добавляется новый функционал. В этом году был зарелизен ES2020 или ES11, теперь мы ожидаем релиза ES2021(ES12), который намечается на середину 2021-го года.
Новый функционал, каждый год добавляемый в JS, проходит через четыре стадии рассмотрения. В этой статье мы обсудим тот функционал, который уже находится на 4-й стадии, то есть на последней и который уже был успешно добавлен в Google Chrome V8.
Функционал, который мы будем обсуждать в этой статье:
String.prototype.replaceAll
Promise.any
Логические операторы и выражения присваивания
Числовые разделители
Intl.ListFormat
dateStyle
и timeStyle
для Intl.DateTimeFormat
String.prototype.replaceAll
В JavaScript метод replace()
заменяет только первый совпадающий элемент в строке. Если нам понадобится заменить все совпадения, то мы сможем сделать только только с помощью регулярных выражений.
Предложенный в ES2020 метод replaceAll()
отдаёт новую строку, где все подходящие символы будут заменены на другие. Это могут быть строки или регулярные выражения, а заменять можно будет на строку или функцию, которая будет отрабатывать при каждом совпадении.
let str = 'I use linux, I love linux'
str = str.replaceAll('linux', 'windows');
console.log(str)
/**** Output ****/
// I use windows, I love windows
Promise.any
В ES2020 нам представят метод Promise.any()
, который резко останавливается и сразу отдаёт значение, как только выполнится первый промис из списка выполняемых промисов. Если выполнение всех промисов закончится неудачей, то будет выдана ошибка.
Этот метод конечно же отличается от Promise.race()
тем, что последний останавливается и выдает промис вне зависимости от результата его выполнения.
Пример 1а: Несмотря на то, что неудачно завершившийся промис заканчивает работу раньше, чем успешно завершившийся. Promise.any()
отдаст первый из успешно завершившихся.
Promise.any([
new Promise((resolve, reject) => setTimeout(reject, 200, 'Third')),
new Promise((resolve, reject) => setTimeout(resolve, 1000, 'Second')),
new Promise((resolve, reject) => setTimeout(resolve, 2000, 'First')),
])
.then(value => console.log(`Result: ${value}`))
.catch (err => console.log(err))
/**** Output ****/
// Result: Second
Пример 1б: Когда все промисы неудачно завершаются, то выдает AggregatorError.
Promise.any([
Promise.reject('Error 1'),
Promise.reject('Error 2'),
Promise.reject('Error 3')
])
.then(value => console.log(`Result: ${value}`))
.catch (err => console.log(err))
/**** Output ****/
// AggregateError: All promises were rejected
Логические операторы и выражения присваивания
В JavaScript существует много выражений присваивания и логических операторов, например как тут:
// Выражение присвивания
let num = 5
num+=10
console.log(num) // 15
// Логический оператор
let num1 = 6
let num2 = 3
console.log(num1 === 6 && num2 === 2) // false
console.log(num1 === 6 || num2 === 2) // true
С помощью нового функционала мы сможем комбинировать логические операторы и выражения присваивания. Ниже вы увидите несколько примеров с &&
, ||
и ??
:
Логический оператор назначения с &&
Тут мы выставляем значение левосторонней переменной только в том случае, если правая имеет значение true
.
let num1 = 5
let num2 = 10
num1 &&= num2
console.log(num1) // 10
// можно записать как
// 1. num1 && (num1 = num2)
// 2. if (num1) num1 = num2
Логический оператор назначения с ||
Тут мы выставляем значение num1
на левую переменную только в том случае, если последняя будет false
.
let num1
let num2 = 10
num1 ||= num2
console.log(num1) // 10
// можно записать как
// 1. num1 || (num1 = num2)
// 2. if (!num1) num1 = num2
Логический оператор назначения с ??
В ES2020 был представлен Nullish Coalescing оператор, который можно совмещать с оператором назначения. Он назначает правую переменную левой переменной только в случае, если последняя имеет значение undefined
или null
.
let num1
let num2 = 10
num1 ??= num2
console.log(num1) // 10
num1 = false
num1 ??= num2
console.log(num1) // false
// можно записать как
// num1 ?? (num1 = num2)
Числовые разделители
С приходом числовых разделителей станет куда проще читать и воспринимать числовые значения, применяя _
(нижнее подчеркивание), раздавая разделители группам цифр. Для примера:
let number = 100_000
console.log(number)
/**** Output ****/
// 100000
Intl.ListFormat
Этот объект принимает два параметра, каждый из которых является опциональным. Первый это заданный язык(локаль), а второй это объект с параметрами у которых есть два свойства — стиль и тип.
new Intl.ListFormat([locales[, options]])
В Intl.ListFormat
есть метод под названием format()
, который получает массив как аргумент и форматирует его разными способами в зависимости от языка.
Ниже есть несколько примеров в которых показаны различные комбинации для локалей.
const arr = ['Pen', 'Pencil', 'Paper']
let obj = new Intl.ListFormat('en', { style: 'short', type: 'conjunction' })
console.log(obj.format(arr))
/**** Output ****/
// Pen, Pencil, & Paper
obj = new Intl.ListFormat('en', { style: 'long', type: 'conjunction' })
console.log(obj.format(arr))
/**** Output ****/
// Pen, Pencil, and Paper
obj = new Intl.ListFormat('en', { style: 'narrow', type: 'conjunction' })
console.log(obj.format(arr))
/**** Output ****/
// Pen, Pencil, Paper
// Итальянский
obj = new Intl.ListFormat('it', { style: 'short', type: 'conjunction' })
console.log(obj.format(arr))
/**** Output ****/
// Pen, Pencil e Paper
// Немецкий
obj = new Intl.ListFormat('de', { style: 'long', type: 'conjunction' })
console.log(obj.format(arr))
/**** Output ****/
// Pen, Pencil und Paper
dataStyle и timeStyle опции для Intl.DateTimeFormat
Intl.DateTimeFormat
это объект конструктор для объектов, которые включают в себя формат даты и отображения времени зависимые от используемого языка. dateStyle
и timeStyle
опции могут быть использованы для запроса специфического отображения даты или времени в заданной длине.
// Только время в коротком формате
let o = new Intl.DateTimeFormat('en' , { timeStyle: 'short' })
console.log(o.format(Date.now()))
// 11:27 PM
// Только время в обычном формате
o = new Intl.DateTimeFormat('en' , { timeStyle: 'medium'})
console.log(o.format(Date.now()))
// 11:27:57 PM
// Время в расширенном формате
o = new Intl.DateTimeFormat('en' , { timeStyle: 'long' })
console.log(o.format(Date.now()))
// 11:27:57 PM GMT+11
// Только дата в сокращенном формате
o = new Intl.DateTimeFormat('en' , { dateStyle: 'short'})
console.log(o.format(Date.now()))
// 10/6/20
// Только дата в обычном формате
o = new Intl.DateTimeFormat('en' , { dateStyle: 'medium'})
console.log(o.format(Date.now()))
// Oct 6, 2020
// Только дата в расширенном формате
o = new Intl.DateTimeFormat('en' , { dateStyle: 'long'})
console.log(o.format(Date.now()))
// October 6, 2020
dateStyle
и timeStyle
используются вместе с разными лингвистическими тегами, как показано на примере ниже:
let abc
// Английский
abc = new Intl.DateTimeFormat('en' , { timeStyle: 'short', dateStyle: 'long'})
console.log(abc.format(Date.now()))
// October 6, 2020 at 11:40 PM
// Итальянский
abc = new Intl.DateTimeFormat('it' , { timeStyle: 'short', dateStyle: 'long'})
console.log(abc.format(Date.now()))
// 6 ottobre 2020 23:40
// Немецкий
abc = new Intl.DateTimeFormat('de' , { timeStyle: 'short', dateStyle: 'long'})
console.log(abc.format(Date.now()))
// 6. Oktober 2020 um 23:40