Last active
November 6, 2023 13:48
-
-
Save dSalieri/de31add7ffedded638a228f2933858d9 to your computer and use it in GitHub Desktop.
Алгоритм SpeciesConstructor
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| /// Эта функция отсылка к спецификационному алгоритму https://tc39.es/ecma262/#sec-speciesconstructor | |
| /// Смысл операции извлечь конструктор для переданного объекта | |
| /* | |
| Наверное вас смущает, что первая строчка кода могла бы решить этот вопрос, | |
| но особенность в том что есть [Symbol.species], через который можно сообщить что использовать значение из | |
| "constructor" вы не хотите, а хотите возспользоваться чем-то другим, решение - [Symbol.species] | |
| */ | |
| function SpeciesConstructor(O, defaultConstructor){ | |
| const C = Reflect.get(O, "constructor"); | |
| if(C === undefined) return defaultConstructor; | |
| const isObject = (o) => typeof o === "object" && o !== null || typeof o === "function"; | |
| if(!isObject(C)) throw TypeError("C is not an Object"); | |
| const S = Reflect.get(C, Symbol.species); | |
| if(S === undefined || S === null) return defaultConstructor; | |
| const isConstructor = (c) => typeof c === "function" && Reflect.has(c.prototype ?? Object.create(null), "constructor"); | |
| if(isConstructor(S)) return S; | |
| throw TypeError("S is not constructor"); | |
| } | |
| /// примеры | |
| SpeciesConstructor({}, Array); /// ƒ Array() { [native code] } | |
| SpeciesConstructor(Promise.resolve(1), Array) /// ƒ Promise() { [native code] } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment