Кратко
СкопированоФункция Array
создаёт новый массив на основе переданного объекта. Объект должен быть либо массивоподобным (как строка или объект arguments
), либо итерируемым (как Set
или Map
).
Как пишется
СкопированоФункция Array
принимает три аргумента, последние два из которых не обязательны:
- Объект, на основе которого создаётся массив.
- Функция преобразования элемента перед его добавлением в массив. Работает как метод
map
.( ) - Значение, которое будет использоваться как
this
в функции из второго параметра.
Возвращает новый массив, составленный из элементов переданного объекта.
Пример
СкопированоМассив из строки
Скопированоconst arr = Array.from('дока')console.log(arr)// ['д', 'о', 'к', 'а']
const arr = Array.from('дока') console.log(arr) // ['д', 'о', 'к', 'а']
Массив из Set
Скопированоconst uniqueNumbers = new Set()uniqueNumbers.add(1)uniqueNumbers.add(2)uniqueNumbers.add(3)const arr = Array.from(uniqueNumbers)// [1, 2, 3]
const uniqueNumbers = new Set() uniqueNumbers.add(1) uniqueNumbers.add(2) uniqueNumbers.add(3) const arr = Array.from(uniqueNumbers) // [1, 2, 3]
Массив из HTMLCollection
СкопированоПолучить URL из всех ссылок на странице:
const linkElements = document.getElementsByTagName('a')const arrLinks = Array.from(linkElements, function(a) { return a.href })
const linkElements = document.getElementsByTagName('a') const arrLinks = Array.from(linkElements, function(a) { return a.href })
Как понять
СкопированоВ JavaScript и браузерных API есть много объектов, которые очень похожи на массив, но не являются им. Объекты могут выглядеть как массив, но не иметь всех методов массива: for
, map
, filter
и так далее.
Такие объекты приходится превращать в массивы для удобства работы с ними или для интеграции с библиотеками. Array
создан, чтобы решить проблему конвертации таких объектов в новый массив.
Array
работает не со всеми объектами. Объект должен обладать одним из двух свойств, чтобы его получилось превратить в массив:
- Элементы объекта проиндексированы и объект имеет свойство
length
. Такие объекты называют массивоподобными, потому что именно эти свойства присущи массиву. Этим свойством обладают объектыarguments
,Node
,List HTML
.Collection - Объект итерируемый, то есть реализует интерфейс
Iterable
. Этим свойством обладают объектыSet
иMap
.
Array
перебирает каждый элемент и добавляет его в новый массив. Если передан второй аргумент, то перед добавлением происходит преобразование элемента.
При создании массива происходит поверхностное копирование (shallow copy) элементов. Если исходный объект содержит итерируемые элементы являющиеся объектами, то эти объекты будут скопированы по ссылке. Изменения будут видны в полученном массиве при их последующем изменении в исходном объекте, и наоборот.
Например:
// Создадим объекты книгconst bookObj1 = { name: 'Война и мир', author: 'Л. Н. Толстой', filmYears: [1913, 1915, 1956]}const bookObj2 = { name: 'Братья Карамазовы', author: 'Ф. М. Достоевский', filmYears: [1915, 1920, 1931, 1969]}// Создадим Set и добавим в него книгиconst bookSet = new Set()bookSet.add(bookObj1)bookSet.add(bookObj2)// Создадим массив из Setconst bookArray = Array.from(bookSet)// Добавим экранизацию 'Войны и мира' в исходный объектbookObj1.filmYears.push(1965)// Изменение отразится и на массивеconsole.log(bookArray[0])// const bookObj1 = {// name: 'Война и мир',// author: 'Л. Н. Толстой',// filmYears: [1913, 1915, 1956, 1965]// }
// Создадим объекты книг const bookObj1 = { name: 'Война и мир', author: 'Л. Н. Толстой', filmYears: [1913, 1915, 1956] } const bookObj2 = { name: 'Братья Карамазовы', author: 'Ф. М. Достоевский', filmYears: [1915, 1920, 1931, 1969] } // Создадим Set и добавим в него книги const bookSet = new Set() bookSet.add(bookObj1) bookSet.add(bookObj2) // Создадим массив из Set const bookArray = Array.from(bookSet) // Добавим экранизацию 'Войны и мира' в исходный объект bookObj1.filmYears.push(1965) // Изменение отразится и на массиве console.log(bookArray[0]) // const bookObj1 = { // name: 'Война и мир', // author: 'Л. Н. Толстой', // filmYears: [1913, 1915, 1956, 1965] // }
На практике
Скопированосоветует Скопировано
🛠 Если вызвать Array
без аргументов, то произойдёт ошибка «TypeError: undefined is not iterable (cannot read property Symbol(Symbol.iterator))».
🛠 В подавляющем большинстве случаев второй и третий аргументы опускаются, но их использование может быть полезным сокращением кода.
Вместо последовательного вызова Array
и .map
:
const name = 'Mike'const spacedLetters = Array.from(name).map(function (letter) { return `*${letter}*`})console.log(spacedLetters)// ['*M*', '*i*', '*k*', '*e*']
const name = 'Mike' const spacedLetters = Array.from(name).map(function (letter) { return `*${letter}*` }) console.log(spacedLetters) // ['*M*', '*i*', '*k*', '*e*']
...можно записать один вызов Array
со вторым аргументом:
const name = 'Mike'const spacedLetters = Array.from(name, function(letter) { return `*${letter}*` })
const name = 'Mike' const spacedLetters = Array.from(name, function(letter) { return `*${letter}*` })
При выполнении этого кода не создаётся промежуточный массив.
🛠 Можно использовать Array
, чтобы генерировать последовательности значений без использования классического цикла for
.
Для этого нужно создать объект, который соответствует требованиям — имеет свойство length
и индексы. Так как размер массива не всегда совпадает с количеством элементов внутри, мы можем создать объект со свойством length
, но без индексированных элементов, и создавать такие элементы с помощью второго аргумента:
const nums = Array.from({length: 4}, function(value, index) { // value будет undefined return index * 2})console.log(nums)// [0, 2, 4, 6]
const nums = Array.from({length: 4}, function(value, index) { // value будет undefined return index * 2 }) console.log(nums) // [0, 2, 4, 6]