Как работает этот конкретный сценарий параметров по умолчанию и деструктуризации? - PullRequest
0 голосов
/ 03 мая 2018

Сегодня я пробовал кое-что и натолкнулся на поведение, которое хотел бы понять.

var b = ({a = 1, b = 1, c = 1}) => a + b + c;

b(); // throws error.

Но если это определено так

var b = ({a = 1, b = 1, c = 1} = 0) => a + b + c;

b() // returns 3
b([]) // returns 3

Разве это не ошибка? Ноль как-то стал здесь объектом? Это как-то эквивалентно следующему?

var b = ({a = 1, b = 1, c = 1} = {}) => a + b + c; // this is possible I guess.

Мой вопрос не в том, как работают обычные параметры уничтожения и параметры по умолчанию, а только в том, как оценивается этот конкретный сценарий.

Может кто-нибудь объяснить мне это?

Ответы [ 5 ]

0 голосов
/ 03 мая 2018
({a = 1, b = 1, c = 1} = something) => {}

просто означает, что something должен быть объектом или может быть преобразован в один, то есть это не может быть null или undefined. 1

Итак, в случае 0 он перехватывает свойства a, b и c 0, то есть (0).a, (0).b, (0).c, все undefined, следовательно, все они по умолчанию равны 1, их предоставленное значение по умолчанию.

0 можно, конечно, привести к объекту Number. Вот почему вы можете сделать (0).toString() или {toString} = 0. Именно это и происходит здесь.

Как правило, это не эквивалентно использованию {} по умолчанию, поскольку при этом будут использоваться свойства пустого объекта (как собственные свойства, так и свойства в цепочке прототипов), а не свойства числа.


1: Наиболее сокращенная форма этой «структурной проверки» - ({} = something). Для деструктурирования массивов это ([] = something), и это означает, что something также должно быть повторяемым . Кстати, эти пустые назначения деструктурирования не создают никаких переменных, они просто выполняют проверку структуры.

0 голосов
/ 03 мая 2018

Причина: В JavaScript компилятор выполняет автоматическое приведение типов, поэтому 0 обрабатывается как «Object (0)», поскольку функция b ожидает объекты в качестве входных данных.

Подробнее: Функция b принимает входные данные как Объект со значениями по умолчанию a, b, c, уничтожая Объект.

так что вызывающая сторона b должна передать объект, если ничего не пропущено, выдается ошибка. Когда что-то передается b, оно пытается извлечь значения a, b, c из переданного объекта. Если что-то передается, оно принимает эти значения, а если ничего не передается, по умолчанию используются значения, указанные в определении

Пример: если вы передадите что-то вроде этого b({a : 10, b: 20}), то по умолчанию значение c будет равно 1, и будет напечатано 31

Для b({a : 10, d: 20}), b и c превращаются в значения по умолчанию и возвращают 12.

Надеюсь, это поможет понять.

0 голосов
/ 03 мая 2018
var b = ({a=1,b=1,c=1})=>a+b+c
b() //throws error.

Ожидается, что в качестве входных данных будут переданы некоторые параметры вместо того, чтобы вы вызывали b (), ничего не передавая.

var b = ({a=1,b=1,c=1} = 0)=>a+b+c 
b() //return 3

Это работает, потому что вы присвоили ему начальное значение {a = 1, b = 1, c = 1} = 0, которое равно 0, и оно создает 3 переменные, которые вы используете a + b + c со значением по умолчанию = 1

0 голосов
/ 03 мая 2018

Уничтожение работ как с массивами, так и с объектами. Из того, что я обнаружил в реструктуризации шаблонов объектов

Шаблон объекта приводит к разрушению источников до объектов доступ к свойствам

Например,

const {length : len} = 'abc'; // len = 3
const {toString: s} = 123; // s = Number.prototype.toString

В вашем случае:

b([]) // return 3 as it arrays destructing
b({a=1,b=2,c=3} =0) // works because of object coercion

Пожалуйста, проверьте эту ссылку для получения дополнительной информации.

0 голосов
/ 03 мая 2018

Он берет прототип примитивного значения и использует его в качестве значения разрушения.

var b = ({ a = 1, b = 1, c = 1, toFixed } = 0) => toFixed.bind(a + b + c)(2);

console.log(b());
...