06. Массивы

Краткое описание методов класса Array

массив.push(...) и массив.pop()

Эти методы позволяют работать с массивом, как со стеком.

Метод push добавляет один или несколько (сколько угодно) элементов в конец массива и возвращает его новую длину.


var st = [];    // Создали пустой массив
st.push(1);     // Получили [1], вернули 1
st.push(2,3);   // Получили [1,2,3], вернули 3
st.push([1,2]); // Получили [1,2,3,[1,2]], вернули 4
st.push(function(x) {return x*x}); // Получили 
                // [1,2,3,[1,2],function(x) {return x*x}], вернули 5
st[3][1] == 2;  // true            
st[4](2) == 4;  // true            

Метод pop удаляет последний элемент массива и возвращает удалённый элемент.


var st = [1,2,3,[1,2],function(x) {return x*x}];
st.pop()(4) == 16 // true, теперь массив: [1,2,3,[1.2]] 
st.pop()[0] == 1  // true, теперь массив: [1,2,3]
st.pop();         // Получили [1,2], вернули 3
st.pop();         // Получили [1], вернули 2
st.pop();         // Получили [], вернули 1
st.pop();         // Получили [], вернули undefined

Если массив пуст, pop не меняет его и возвращает значение undefined.

массив.unshift(...) и массив.shift()

Эти методы похожи на push и pop, но работают не с концом массива, а с его началом.

Метод unshift добавляет один или несколько (сколько угодно) элементов в начало массива (в заданном порядке) и возвращает новую длину массива.


var qu = [];        // Создали пустой массив
qu.unshift(3);      // Получили [3], вернули 1
qu.unshift(1,2);    // Получили [1,2,3], вернули 3
qu.unshift([1,2]);  // Получили [[1,2],1,2,3], вернули 4
qu.unshift(function(x) {return x*x}); // Получили 
                    // [function(x) {return x*x},[1,2],1,2,3], вернули 5
qu[1][0] == 1;      // true
qu[0](10) == 100;   // true

Метод shift удаляет первый (с номером 0) элемент массива и возвращает удалённый элемент.


var qu = [function(x) {return x*x},[1,2],1,2,3];
qu.shift()(qu[0][1]) == 4; // true, теперь массив: [[1,2],1,2,3]
qu.shift()[0] == 1;        // true, теперь массив: [1,2,3]
qu.shift();                // Получили [2,3], вернули 1
qu.shift();                // Получили [3], вернули 2
qu.shift();                // Получили [], вернули 3
qu.shift();                // Получили [], undefined

Если массив пуст, shift не меняет его и возвращает значение undefined.

массив.splice(начало, количество, значение, ...)

Универсальный метод для вставки и удаления элементов массива.

Аргументы:

начало Индекс элемента, с которого надо начать вставку и (или) удаление.
количество Количество элементов, которые должны быть удалены из массива, начиная с элемента, заданного аргументом начало. Если удалять не надо, передайте через этот аргумент число 0.
значение, ... Элементы, которые должны быть вставлены в массив, начиная с элемента, заданного аргументом начало. Эти аргументы могут присутствовать в любом количестве (в том числе и в количестве 0, то есть отсутствовать).

Возвращаемое значение: массив, содержащий удаленные из массива элементы, если они есть.


var a = [0,1,2,3,4,5,6,7,8,9];                          
a.splice(5,5);       // Получили [0,1,2,3,4], вернули [5,6,7,8,9]
a.splice(1,2);       // Получили [0,3,4], вернули [1,2]
a.splice(1,1,10,20); // Получили [0,10,20,4], вернули [3]
a.splice(1,1,[1,2]); // Получили [0,[1,2],20,4], вернули [10]
a[1][1] == 2;        // true

// Добавление в начало
a.splice(0,0,100);       // Получили [0,100,[1,2],20,4], вернули []

// Добавление в конец
a.splice(a.length,0,50); // Получили [100,[1,2],20,4,50], вернули []

// Добавление перед i-ым элементом
var a = [0,1,2,3,4,5];                          
var i = 3;
a.splice(i,0,"кот"); // Получили [0,1,2,"кот",3,4,5], вернули []

// Добавление на место i-го элемента
var a = [0,1,2,3,4,5];                          
var i = 3;
a.splice(i,1,"кот"); // Получили [0,1,2,"кот",4,5], вернули [3]

// Добавление после i-го элемента
var a = [0,1,2,3,4,5];                          
var i = 3;
a.splice(i+1,0,"кот"); // Получили [0,1,2,3,"кот",4,5], вернули []
массив.slice(начало, законец)

Возвращает массив, содержащий фрагмент исходного массива. Исходный массив не меняется.

Аргументы:

начало Индекс элемента, с которого начинается фрагмент. Если задано отрицательное значение, отсчет выполняется с конца (-1 обозначает последний элемент).
законец Индекс элемента, расположенного непосредственно за концом фрагмента. Если аргумент не указан, конец фрагмента совпадает с концом массива. Если задано отрицательное значение, отсчет выполняется с конца (-1 обозначает последний элемент).

Возвращаемое значение: массив, содержащий выделенный фрагмент.


var a = [0,1,2,3,4,5];                          
a.slice(1);       // Возвращает [1,2,3,4,5]
a.slice(2,4);     // Возвращает [2,3]
a.slice(-2,-1);   // Возвращает [4]
a.slice(-2);      // Возвращает [4,5]
// Первый элемент
a.slice(0,1);      // Возвращает [1]
// Без первого элемента
a.slice(1);        // Возвращает [1,2,3,4,5]
// Последний элемент
a.slice(-1);       // Возвращает [5]
// Без последнего элемента
a.slice(0,-1);     // Возвращает [0,1,2,3,4]
массив.concat(значение,...)

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

Аргументы:

значение, ... Элементы, которые должны быть добавлены в конец исходного массива (исходный массив не меняется).

Возвращаемое значение: массив, образуемый добавлением в конец исходного массива элементов, задаваемых аргументами метода.


var a = [0,1,2];                          
a.concat();        // Возвращает исходный массив [0,1,2]
a.concat(3);       // Возвращает массив [0,1,2,3]
a.concat(3,4,5);   // Возвращает массив [0,1,2,3,4,5]

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


a.concat([3,4]); // Возвращает массив [0,1,2,3,4]

Но это правило не работает рекурсивно:


a.concat([3,[4,5]]); // Возвращает массив [0,1,2,3,[4,5]]
a.concat([3,[4,5]])[4][1] == 5; // true
массив.join(разделитель)

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

Аргументы:

разделитель  Строка, необязательный аргумент. Если аргумент не задан, в качестве разделителя используется запятая.

Возвращаемое значение: строка, которая получается преобразованием каждого элемента в строку и объединением их с разделителем между элементами.

Метод join класса Array и метод split класса String являются взаимно обратными. Метод split разбивает строку на элементы массива, метод join превращает массив в строку.


var a = "12345".split("")  // Равно ["1","2","3","4","5"]
a.join("");                // Равно "12345"

var a = [1,2,3,4,5];
a.join();                 // Равно "1,2,3,4,5"
a.join(", ");             // Равно "1, 2, 3, 4, 5"
a.join(" + ");            // Равно "1 + 2 + 3 + 4 + 5"

var x;
var a = [1,x==1,{}];
a.join("");               // Равно "1false[object Object]"

Пояснение. Число 1 преобразуется в строку "1". Это понятно.

Вычисляется значение выражения x==1. Значение x есть undefined, значит, значением выражения является логическое значение false. Оно преобразуется в строку "fаlse".

Для преобразования объекта в строку всегда вызывается метод toString(). Это стандартный метод класса Object. Он преобразует объект в строку "[object Object]".

массив.reverse()

Меняет порядок следования элементов в массиве на обратный. Метод ничего не возвращает.


var a = [0,1,2,3,4,5];
a.reverse();           // Получили [5,4,3,2,1,0] 
массив.sort(функция)

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

Аргументы:

функция Необязательный аргумент. Если задана то, должна принимать два аргумента a и b и возвращать одно из следующих значений:
  • Отрицательное число означает, что а должно находится перед b.
  • Ноль означает, что a имеет тот же порядок следования, что и b (то есть порядок следования a и b относительно друг друга не важен).
  • Положительное число означает, что а должно находится после b.

Если функция не задана, элементы массива сортируются в порядке, который определяет таблица кодирования символов («алфавитный порядок»).

Возвращаемое значение: возвращает ссылку на исходный массив (который отсортирован). Заметьте, возвращается ссылка, а не сам массив.

Описание работы метода

Сначала посмотрим, как работает метод при вызове без аргумента («алфавитный порядок»).


var a =["р","о","б","о","т","л","а","н","д","и","я"];
a.sort(); // ["а","б","д","и","л","н","о","о","р","т","я"]                    

var a = [45,2,100,311,46];               
a.sort(); // [100,2,311,45,46]

var a = [1," ","ё","е","я","Я"];               
a.sort(); // [" ",1,"Я","е","я","ё"]

Как видите, «алфавитный порядок» не всегда соответствует нашим ожиданиям. Этот порядок задает кодовая таблица символов. Символ считается «больше», если больше его код в этой таблице.

Более интересен вызов метода с аргументом. В качестве аргумента указывается функция, которая определяет порядок пары элементов. Сортировка ведь сводится к проверке пар. Каждый раз когда метод sort решает, в каком порядке должны следовать два элемента (a и b), он вызывает эту функцию и смотрит на возвращённое значение:

  • Отрицательное число означает, что а должно находится перед b.
  • Ноль означает, что a имеет тот же порядок следования, что и b (то есть порядок следования a и b относительно друг друга не важен).
  • Положительное число означает, что а должно находится после b.

Например, нужно отсортировать числовой массив в порядке возрастания значений:


function f(a,b) 
{
  return a-b;
}
var a = [45,2,100,311,46];               
a.sort(f); // [2,45,46,100,311]

На самом деле, нет никакого резона определять эту функцию, как глобальное свойство f объекта window. Разумно (при однократном использовании) задать ее без всякого имени при помощи литерала:


var a = [45,2,100,311,46];               
a.sort(function(a,b){return a-b;}); // [2,45,46,100,311]

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


var a = [45,2,2,100,311,46];               
a.sort(function(a,b){return b-a;}); // [311,100,46,45,2,2]

А вот так можно задать сортировку в порядке возрастания синусов чисел в массиве:


var a = [45,2,2,100,311,46];               
a.sort(function(a,b){return Math.sin(a)-Math.sin(b);}); // [100,311,45,46,2,2]

А вот сортировка массива, содержащего строки, по их длине (в порядке возрастания длин):


var a = ["роботландия","","кот","1","24"];               
a.sort(function(a,b)
       {
         return a.length-b.length;
       });  // ["","1","24","кот","роботландия"]
массив.toString()

Этот метод класса Object переопределяется в классе Array следующим образом.

Метод toString массива преобразует в строку каждый элемент (вызывая их методы toString), затем полученные строки объединяются в одну строку, используя в качестве разделителя запятую. Получается, что метод toString работает так же, как метод join().


var a = [1,true,"кот",[4,[5,6]]];               
a.toString(); // Возвращает строку "1,true,кот,4,5,6"
a.toString().replace(/,/g,""); // Возвращает строку "1trueкот456"
a.toString().replace(/,/g,"+"); // Возвращает строку "1+true+кот+4+5+6"

Последние две строки демонстрируют приём программирования под названием «цепочка вычислений». Берите на вооружение! Эффективно (не заводятся промежуточные переменные) и красиво. Цепочки вычислений активно используются при работе с библиотекой JQuery.