02.i ES6 Parameters
В ES6 работа с параметрами функции была существенно расширена:
default parameter values
rest parameters (
varargs
)deconstructing on parameters
spread arguments
Default Parameters
Параметр по умолчанию используется при отсутствующем параметре или равном undefined
. При передаче любого значения, кроме undefined
, включая пустую строку, ноль или null
, параметр считается переданным, и значение по умолчанию не используется. Параметры по умолчанию могут быть не только значениями, но и выражениями и вызовами функций.
Традиционный прием для эмуляции параметров по умолчанию в ES5:
function pair(x, y) {
var x = x || 0;
var y = y || 0;
return [x, y];
}
Синтаксис ES6:
function showMenu(title = "Без заголовка", width = 100, height = 200) {
alert(`${title} ${width} ${height}`);
}
function sayHi(who = getCurrentUser().toUpperCase()) {
alert(`Привет, ${who}!`);
}
Параметры могут ссылаться друг на друга в порядке своего объявления:
function func(x = 1, y = x) {
return [x, y];
}
Значения параметров по умолчанию, а так же функции, используемы для параметров по умолчанию не видят область видимости, формируемую основным телом функции.
Если необходимо, что бы функция обладала обязательным параметром, то можно использовать следующий прием:
function mandatory() {
throw new Error("Missing parameter");
}
function foo(mustBeProvided = mandatory()) {
return mustBeProvided;
}
...rest
parameters
...rest
parametersОператор rest (…
) оператор записывает все оставшиеся переданные аргументы функции в соответствующий массив, с методами map
, forEach
и другими, в отличие от arguments
:
return (function(foo, ...args) {
return args instanceof Array && args + "" === "bar,baz";
})("foo", "bar", "baz");
Использование rest
позволяет полностью заменить использование псевдо-массива arguments
. Сочетая rest и деструктуризацию можно иметь как массив, так и отдельные параметры:
function foo(...args) {
const [x = 0, y = 0] = args;
console.log('Arity: '+args.length);
···
}
Destruction in Parameters
Если хочется, чтобы функция могла быть вызвана вообще без аргументов — нужно добавить ей параметр по умолчанию — уже не внутрь деструктуризации, а в самом списке аргументов:
const options = {
title: "Меню",
width: 100,
height: 200
};
function showMenu({ title, width, height }) {
alert(`${title} ${width} ${height}`); // Меню 100 200
}
function showMenu({
title = "Заголовок",
width: w = 100,
height: h = 200
} = {}) {
alert(`${title} ${w} ${h}`);
}
showMenu(); // Заголовок 100 200
Option Object (Named parameters)
Можно реализовывать именованные параметры через передачу объекта (option object):
selectEntries({start: 3, end: 20, step: 2});
selectEntries({step: 2});
selectEntries({end: 20, start: 3});
selectEntries();
function selectEntries(options) {
options = options || {};
const start = options.start || 0;
const end = options.end || getDbLength();
const step = options.step || 1;
...
}
В ES6 подобную логику можно упростить при помощи деструкции параметров вместе со значениями по умолчанию:
function selectEntries({start = 0, end = getDbLength(), step = 1}) {
...
}
spread
operator
spread
operatorОператор spread
применяется к любой итерируемой структуре и преобразует её в последовательность значений. Чаще всего используется при вызове функции для преобразования структуры в последовательность аргументов, передаваемых в функцию.
> Math.max(-1, 5, 11, 3)
11
> Math.max(...[-1, 5, 11, 3])
11
> Math.max(-1, ...[-1, 5, 11], 3)
11
Части массива могут быть преобразованы в значения:
> [1, ...[2,3], 4]
[1, 2, 3, 4]
Оператор spread
выглядит так же как и оператор rest
(...
) но противоположен ему по смыслу. Оператор rest
используется только внутри функции, тогда как оператор spread
только при вызове функции или конструктора.
Вместо массива со spread
можно использовать любые итерируемые структуры, такие как строки, генераторы, объекты (?).
При строках:
// strings
return Math.max(..."1234") === 4;
В массивах:
// strings
["a", ..."bcd", "e"][3] === "d";
const x = ["a", "b"];
const y = ["c"];
const z = ["d", "e"];
const arr = [...x, ...y, ...z]; // ['a', 'b', 'c', 'd', 'e']
Преобразование любой итерируемой сущности в массив:
const map0 = new Map([
[1, "a"],
[2, "b"],
[3, "c"]
]);
// copy map
const map1 = new Map([...map0]);
// spread set into array
const set = new Set([11, -1, 6]);
const arr = [...set]; // [11, -1, 6]
При генераторе
// generator
const iterable = (function*() {
yield 1;
yield 2;
yield 3;
})();
Math.max(...iterable) === 3;
// generators
const iterable = (function*() {
yield "b";
yield "c";
yield "d";
})();
["a", ...iterable, "e"][3] === "d";
Last updated
Was this helpful?