.concat()

Возвращает новый массив, полученный при объединении нескольких массивов.

Время чтения: 5 мин

Кратко

Скопировано

Метод concat() объединяет исходный массив с одним или несколькими указанными массивами или другими значениями и возвращает новый массив. Метод не меняет массивы, участвующие в объединении.

Пример

Скопировано

Объединим два массива в новый массив. Обратите внимание — исходный массив не изменился:

        
          
          const months = ['март', 'апрель', 'май']const summer = ['июнь', 'июль', 'август']const favoriteMonths = months.concat(summer)console.log(favoriteMonths)// ['март', 'апрель', 'май', 'июнь', 'июль', 'август']console.log(months)// ['март', 'апрель', 'май']
          const months = ['март', 'апрель', 'май']
const summer = ['июнь', 'июль', 'август']
const favoriteMonths = months.concat(summer)

console.log(favoriteMonths)
// ['март', 'апрель', 'май', 'июнь', 'июль', 'август']

console.log(months)
// ['март', 'апрель', 'май']

        
        
          
        
      

Объединим три массива в новый массив, используя в качестве исходного пустой массив:

        
          
          const numbers = [2, 12, 85]const strings = ['06', 'это', 'твой', 'номер']const result = [].concat(numbers, strings)console.log(result)// [2, 12, 85, '06', 'это', 'твой', 'номер']
          const numbers = [2, 12, 85]
const strings = ['06', 'это', 'твой', 'номер']
const result = [].concat(numbers, strings)

console.log(result)
// [2, 12, 85, '06', 'это', 'твой', 'номер']

        
        
          
        
      

Как пишется

Скопировано

concat() принимает в качестве аргументов элементы, объединяемые в новый массив.

concat() возвращает новый массив, полученный при объединении.

Если метод без аргументов был вызван для массива, возвращается поверхностная копия (shallow copy) исходного массива:

        
          
          const numbers = [1, 2, 3, 4]const copyNumbers = numbers.concat()console.log(copyNumbers)// [1, 2, 3, 4]console.log(numbers)// [1, 2, 3, 4]
          const numbers = [1, 2, 3, 4]
const copyNumbers = numbers.concat()

console.log(copyNumbers)
// [1, 2, 3, 4]

console.log(numbers)
// [1, 2, 3, 4]

        
        
          
        
      

В качестве аргументов могут выступать не только массивы, но и значения других типов:

        
          
          const numbers = [1, 2, 3]const result = numbers.concat(  4, 'five', null, {name: 'six'}, [[7]])console.log(result)// [1, 2, 3, 4, 'five', null, {name: 'six'}, [7]]
          const numbers = [1, 2, 3]
const result = numbers.concat(
  4, 'five', null, {name: 'six'}, [[7]]
)

console.log(result)
// [1, 2, 3, 4, 'five', null, {name: 'six'}, [7]]

        
        
          
        
      

Метод concat() можно вызвать и для значений других типов (например: строка, число, объект). Если this является значением примитивного типа (строка, число, true или false), то оно преобразуется в объект.

Подробнее о преобразовании в объект

Для примитивных значений будет создан объект-обёртка соответствующего типа, например: trueBoolean, 'строка'String, 48Number.

Для undefined и null преобразование в объект выполнено быть не может, так как эти значения не имеют объектов-обёрток.

Примеры использования метода concat(), когда исходным значением не является массив:

        
          
          const concatFn = Array.prototype.concatconst str = 'я строка'console.log(concatFn.call(str))// [ [String: 'я строка'] ]const number = 42console.log(concatFn.call(number, 21))// [ [Number: 42], 21 ]
          const concatFn = Array.prototype.concat
const str = 'я строка'
console.log(concatFn.call(str))
// [ [String: 'я строка'] ]

const number = 42
console.log(concatFn.call(number, 21))
// [ [Number: 42], 21 ]

        
        
          
        
      

В случае попытки использовать undefined или null как исходное значение метода Array.prototype.concat, будет вызвано исключение TypeError.

        
          
          try {  console.log(concatFn.call(null))} catch(err) {  console.error('Поймали ошибку! Вот она:', err.message)}// Поймали ошибку! Вот она:// Array.prototype.concat called on null or undefined
          try {
  console.log(concatFn.call(null))
} catch(err) {
  console.error('Поймали ошибку! Вот она:', err.message)
}
// Поймали ошибку! Вот она:
// Array.prototype.concat called on null or undefined

        
        
          
        
      

Как понять

Скопировано

concat() обычно используется когда необходимо получить новый массив путём объединения нескольких массивов. В отличие от метода splice(), который может использоваться для добавления элементов к исходному массиву, метод concat() создаёт новый массив и не изменяет исходный.

Если аргумент содержит неодномерный массив, то этот массив будет добавлен как один элемент:

        
          
          const numbers = [1, 2, 3]console.log(numbers.concat([4, [5, 6]]))// [1, 2, 3, 4, [5, 6]]
          const numbers = [1, 2, 3]
console.log(numbers.concat([4, [5, 6]]))
// [1, 2, 3, 4, [5, 6]]

        
        
          
        
      

Стандартное поведение метода можно изменить с использованием Symbol.isConcatSpreadable.

Подробнее об использовании `Symbol.isConcatSpreadable`

Согласно спецификации ECMAScript, для изменения поведения метода может использоваться специальное свойство Symbol.isConcatSpreadable.

Если значением этого свойства для массива является false, то он будет добавлен как один элемент:

        
          
          const numbers = [1, 2, 3]const otherNumbers = [4, 5, 6]otherNumbers[Symbol.isConcatSpreadable ] = falseconsole.log(numbers.concat(otherNumbers))// [1, 2, 3, [4, 5, 6, [Symbol(Symbol.isConcatSpreadable)]: false ]]//           ------------------------------------------------------
          const numbers = [1, 2, 3]

const otherNumbers = [4, 5, 6]
otherNumbers[Symbol.isConcatSpreadable ] = false

console.log(numbers.concat(otherNumbers))
// [1, 2, 3, [4, 5, 6, [Symbol(Symbol.isConcatSpreadable)]: false ]]
//           ------------------------------------------------------

        
        
          
        
      

Если значением этого свойства для массивоподобного объекта является true, то его свойства-элементы будут добавлены по отдельности:

        
          
          const numbers = [1, 2, 3]const arrayLike = {  [Symbol.isConcatSpreadable ]: true,  '0': 4,  '1': 5,  '2': 6,  length: 3}console.log(numbers.concat(arrayLike))// [1, 2, 3, 4, 5, 6]console.log(numbers.concat({''}))
          const numbers = [1, 2, 3]
const arrayLike = {
  [Symbol.isConcatSpreadable ]: true,
  '0': 4,
  '1': 5,
  '2': 6,
  length: 3
}

console.log(numbers.concat(arrayLike))
// [1, 2, 3, 4, 5, 6]

console.log(numbers.concat({''}))

        
        
          
        
      

Подсказки

Скопировано

💡 Если один из массивов имеет незаполненные элементы, то при выполнении concat() возвращаемый массив тоже будет содержать незаполненные элементы:

        
          
          const colors = ['crimson', , 'purple']console.log(colors.concat(['magenta']))// ['crimson', <1 empty item>, 'purple', 'magenta']
          const colors = ['crimson', , 'purple']
console.log(colors.concat(['magenta']))
// ['crimson', <1 empty item>, 'purple', 'magenta']

        
        
          
        
      

💡 Если исходный массив или один из аргументов содержит объекты, то возвращаемый в результате работы concat() массив будет содержать для них ссылки, а не новые объекты. Таким образом, последующее изменение объекта будет видно в созданном массиве и наоборот:

        
          
          const skills = [{name: 'HTML'}, {name: 'CSS'}, {name: 'JS'}]// Добавим новый элементconst result = skills.concat([{name: 'Python'}]);console.log(result)// [{name: 'HTML'}, {name: 'CSS'}, {name: 'JS'}, {name: 'Python'}]// Изменим элемент исходного массиваskills[1].level = 'C'console.log(skills)// [{name: 'HTML'}, {name: 'CSS', level: 'C'}, {name: 'JS'}]// Увидим изменения в созданном массивеconsole.log(result)// [//  { name: 'HTML'},//  { name: 'CSS', level: 'C'},//  { name: 'JS' },//  { name: 'Python' }// ]
          const skills = [{name: 'HTML'}, {name: 'CSS'}, {name: 'JS'}]

// Добавим новый элемент
const result = skills.concat([{name: 'Python'}]);
console.log(result)
// [{name: 'HTML'}, {name: 'CSS'}, {name: 'JS'}, {name: 'Python'}]

// Изменим элемент исходного массива
skills[1].level = 'C'

console.log(skills)
// [{name: 'HTML'}, {name: 'CSS', level: 'C'}, {name: 'JS'}]

// Увидим изменения в созданном массиве
console.log(result)
// [
//  { name: 'HTML'},
//  { name: 'CSS', level: 'C'},
//  { name: 'JS' },
//  { name: 'Python' }
// ]