6. Массивы (Java. Базовый курс)

6. Массивы (Java. Базовый курс)


Дата публикации 30.01.2021



На данном уроке разберём что такое массивы, какие виды массивов бывают и как их использовать при разработке программ на Java.

Массивы

Часто на практике приходится работать с целыми наборами данных. Например для календаря нам нужен список названий месяцев, но как его хранить? Создавать 12 переменных и писать большое количество кода для работы с этими переменными? Это плохое решение, оно громоздкое, запутанное и неудобное. К счастью в языке Java есть отличная альтернатива - массивы.

Массив позволяет хранить целый набор данных определённого типа. По большому счёту массив можно представить себе как пронумерованный список или в более сложном случае - таблица. Массивы очень широко используются в приложениях и очень сильно упрощают обработку информации.

 

Одномерный массив

Одномерный массив представляет собой список однотипных элементов. На рисунке ниже приведён пример одномерного массива из 8 элементов:

Одномерный массив

В данном примере в качестве элементов массива выступают различные числа. Кроме этого, каждой ячейке массива соответствует свой индекс, по которому можно получить значение, записанное в ячейку. Обратите внимание что нумерация элементов массива начинается с нуля, это очень важный момент!

Общая форма объявления массива выглядит так:

тип_данных[] имя_массива = new тип_данных[размер_массива];

Напишем простую программу, которая по номеру месяца будет выводить его название:

Пример работы с одномерным массивом

В строке 8 инициализируется массив строк months размером в 12 элементов - ровно столько нам нужно для хранения всех названий месяцев:

String[] months = new String[12];

В строках с 9 по 20 в каждый элемент массива months записывается название месяца. Обращение к элементу идёт по его индексу в квадратных скобках - таким образом мы можем как записать данные в ячейку, так и прочитать. Важный момент - первый элемент имеет индекс 0, как я уже писал выше.

months[0] = "январь";
months[1] = "февраль";
months[2] = "март";
months[3] = "апрель";
months[4] = "май";
months[5] = "июнь";
months[6] = "июль";
months[7] = "август";
months[8] = "сентябрь";
months[9] = "октябрь";
months[10] = "ноябрь";
months[11] = "декабрь";

После того как массив заполнен элементами, программа просит пользователя ввести номер месяца и сохраняет его в переменную number:

Scanner input = new Scanner(System.in);
System.out.println("Введите номер месяца:");
int number = input.nextInt();

Далее в строке 26 программа выводит в консоль название месяца, которое достаёт из массива по индексу. Так как нумерация индексов идёт с нуля, то мы должны из number вычесть единицу, чтобы получить правильное название месяца. Например 5 месяц в году это май, но в массиве значение “май” хранится в элементе с индексом 4, поэтому когда пользователь введёт номер 5, мы должны вычесть из него 1 и получим 4:

System.out.println(months[number-1]);

В данном случае я не сделал проверку на корректность ввода данных, поэтому если пользователь введёт неправильное число, например 100, то приложение выдаст ошибку ArrayIndexOutOfBoundsException. Это значит что была попытка обратиться к несуществующему элементу массива.

Полный листинг программы:

package ru.akutepov.example1;

import java.util.Scanner;

public class MonthByNumber {

    public static void main(String[] args) {
        String[] months = new String[12];
        months[0] = "январь";
        months[1] = "февраль";
        months[2] = "март";
        months[3] = "апрель";
        months[4] = "май";
        months[5] = "июнь";
        months[6] = "июль";
        months[7] = "август";
        months[8] = "сентябрь";
        months[9] = "октябрь";
        months[10] = "ноябрь";
        months[11] = "декабрь";

        Scanner input = new Scanner(System.in);
        System.out.println("Введите номер месяца:");
        int number = input.nextInt();

        System.out.println(months[number-1]);
    }

}

Данный пример выглядит довольно громоздко, но есть способ его упростить. Познакомимся с ещё одной формой инициализации массива в Java:

тип_данных[] имя_массива = {элемент0, элемент1, элемент2, ..., элементN} ;

Эта форма позволяет заполнять массив значениями сразу во время его инициализации, что сокращает количество кода.

Перепишем программу и посмотрим что получится:

Пример использования одномерного массива

Так гораздо лучше - код уже не выглядит таким громоздким, при этом логика осталась та же самая. В зависимости от ситуации можно использовать любую из форм инициализации массива.

Полный листинг программы:

package ru.akutepov.example2;

import java.util.Scanner;

public class MonthByNumber {

    public static void main(String[] args) {
        String[] months = {"январь", "февраль", "март", "апрель", "май", "июнь", "июль", "август", "сентябрь",
                "октябрь", "ноябрь", "декабрь"};

        Scanner input = new Scanner(System.in);
        System.out.println("Введите номер месяца:");
        int number = input.nextInt();

        System.out.println(months[number - 1]);
    }

}

Пример работы полученной программы:

Пример работы программы

Эту программу можно было бы написать без использования массива, например делать проверку номера месяца через оператор switch и выводить соответсвующее название. При этом решение с оператором switch тоже было бы вполне рабочим, но не таким красивым. Из этого следует вывод, что любую задачу можно решить несколькими способами и программист должен уметь выбрать оптимальное решение.

 

Многомерные массивы

В языке Java многомерные массивы представляют собой массивы массивов. Самый распространённый вид многомерных массивов - двумерные массивы

Рассмотрим пример объявления такого массива:

int[][] a = new int[5][5];

В данном примере был проинициализирован двумерный массив a размером 5 на 5, который можно представить ввиде таблицы:

a[0][0]

a[0][1]

a[0][2]

a[0][3]

a[0][4]

a[1][0]

a[1][1]

a[1][2]

a[1][3]

a[1][4]

a[2][0]

a[2][1]

a[2][2]

a[2][3]

a[2][4]

a[3][0]

a[3][1]

a[3][2]

a[3][3]

a[3][4]

a[4][0]

a[4][1]

a[4][2]

a[4][3]

a[4][4]

Если для доступа к элементу одномерного массива нужно указать один индекс, то для доступа к элементу двумерного массива указываются уже два индекса. Левый индекс это номер строки, правый индекс это номер столбца условной таблицы.

Для получения значения из опредённой ячейки нужно указывать 2 индекса, например a[3][1]. Если указать только 1 индекс, то будет получена целая строка из таблицы в виде одномерного массива. Например a[2] вернёт нам элементы 3-ей строки.

В Java допускаются и n-мерные массивы, вот общий синтаксис объявления таких массивов:

тип_данных[][]...[] имя_массива = new тип_данных[размер1][размер2]...[размерN];

Используются такие массивы крайне редко и их трудно изобразить графически, но смысл остаётся тот же.

Посмотрим на практическом примере как работать с двумерным массивом. Для этого усложним предыдущую задачу - вместе с названием месяца будем выводить количество дней в выбранном месяце:

Пример работы с двумерным массивом в Java

Вместо одномерного массива у нас теперь двумерный массив размером 2 на 12. В первая строка массива - названия месяцев, вторая строка - информация о количестве дней в месяце.

String[][] months = {
                {"январь", "февраль", "март", "апрель", "май", "июнь", "июль", "август", "сентябрь", "октябрь", "ноябрь", "декабрь"},
                {"31 день", "28/29 дней", "31 день", "30 дней", "31 день", "30 дней", "31 день", "31 день", "30 дней", "31 день", "30 дней", "31 день"}
};

В строке 17 обращение к элементу массива теперь по 2 индексам - индекс строки и индекс столбца:

System.out.println(months[0][number - 1] + " - " + months[1][number - 1]);

Полный листинг программы:

package ru.akutepov.example3;

import java.util.Scanner;

public class MonthByNumber {

    public static void main(String[] args) {
        String[][] months = {
                {"январь", "февраль", "март", "апрель", "май", "июнь", "июль", "август", "сентябрь", "октябрь", "ноябрь", "декабрь"},
                {"31 день", "28/29 дней", "31 день", "30 дней", "31 день", "30 дней", "31 день", "31 день", "30 дней", "31 день", "30 дней", "31 день"}
        };

        Scanner input = new Scanner(System.in);
        System.out.println("Введите номер месяца:");
        int number = input.nextInt();

        System.out.println(months[0][number - 1] + " - " + months[1][number - 1]);
    }

}

Вот как теперь работает наша программа:

Пример работы программы на Java

 

Получение длины массива

Часто бывает удобно программно узнать длину массива и Java предоставляет такую возможность. Для этого можно воспользоваться свойством length:

имя_массива.length

Это особенно удобно в циклах, когда нужно перебрать все элементы массива. Например выведем в столбик все названия месяцев:

Пример перебора элементов массива в Java

В данном случае я задал для цикла условие i < months.length, таким образом, когда переменная i станет равно 12, цикл завершит свою работу. Последним из массива будет извлечён элемент с индексом 11 (помним что нумерация элементов начинается с 0).

Полный листинг программы:

package ru.akutepov.example4;

public class Months {

    public static void main(String[] args) {
        String[] months = {"январь", "февраль", "март", "апрель", "май", "июнь", "июль", "август", "сентябрь", "октябрь", "ноябрь", "декабрь"};

        for (int i = 0; i < months.length; i++) {
            System.out.println(months[i]);
        }
    }

}

Ещё удобнее перебирать элементы массива с помощью цикла foreach:

Перебор элементов массива циклом foreach в Java

Такая запись выглядит лаконичнее и легче читается. Смысл при этом остаётся тот же - цикл перебирает все элементы массива, но теперь каждый элемент записывается в переменную month, которая в теле цикла выводится в консоль.

Полный листинг программы:

package ru.akutepov.example5;

public class Months {

    public static void main(String[] args) {
        String[] months = {"январь", "февраль", "март", "апрель", "май", "июнь", "июль", "август", "сентябрь", "октябрь", "ноябрь", "декабрь"};

        for (String month : months) {
            System.out.println(month);
        }
    }

}

Результат работы программы выглядит следующим образом:

Вывод элементов массива в консоль в Java

 

Домашнее задание

  1. Дан одномерный массив размером 10 элементов. Заполнить массив целыми числами и найти максимальное и минимальные числа в массиве. Вывести результат на экран.
  2. Дан одномерный массив размером 10 элементов. Заполнить массив целыми числами и определить являются ли элементы массива возрастающей последовательностью.
  3. Дан двумерный массив размером 5 на 10 элементов. Заполнить его произвольными значениями. Все элементы больше 5 заменить на 0.

< Предыдущий урок   Следующий урок >