Хранение данных.

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

 

Массивы. Введение.

Для того чтобы было удобно работать с большим количеством данных, группе ячеек дают общее имя. Такую группу ячеек называют массивом.
Массив – это группа ячеек памяти одинакового типа, расположенных рядом и имеющих общее имя. Каждая ячейка в группе имеет уникальный номер.

При работе с массивами надо научиться решать три задачи:
• выделять память нужного размера под массив;
• записывать данные в нужную ячейку;
• читать данные из ячейки.

Создание массива.

При создании массива в памяти выделяется место (определенное число ячеек).
1) Массивы можно создать простым перечислением элементов:
int[] nums = new int[] { 1, 2, 3, 5 };

int обозначает, что в массиве все объекты - целые число. На месте int может быть любой другой тип данных. Например, 
string[] names = ["Вася", "Петя", "Федя"];

2) Можно не сразу указать значения массива, а просто создать массив нужной нам длины.
int[] nums = new int[4];
3) Массив всегда "знает" свой размер. Размер массива a можно узнать так:
a.Length;
Часто размер массива хранят в отдельной переменной, чтобы была возможность легко изменить программу для работы с другим размером массива. Пример:
int N = 10;          // в переменной N храним размер массива
int[] nums = new int[4];      // создаем массив размера N
Console.Write(nums.Length);  // выводим размер массива
Размер массива можно задавать с клавиатуры.

Обращение к элементу массива.

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

Запомните: нумерация массивов в C# начинается с нуля.

Примеры обращения к массиву A:
int x = (A[3] + 5) * A[1] // прочитать значения A[3] и A[1]
A[0] = x + 6              // записать новое значение в A[0]
Разберем программу работы с элементами массива.
int i = 1;
int[] A = new int[5];  //создаем массив из 5 элементов 
A[0] = 23;    // в каждый из 5 элементов массива (индексы от 0 до 4)
A[1] = 12;    // записываем определенное значение
A[2] = 7;
A[3] = 43;
A[4] = 51;
A[2] = A[i] + 2*A[i-1] + A[2*i]; // изменим значение элемента с индексом 2, на результат выражения
                                 // т.к i=1, то подставляя значение переменной i в выражение получим
                                // следующее выражение  A[2] = A[1] + 2*A[0] + A[2];
Console.Write((A[2] + A[4]));

В результате выполнения данной программы на экране появится значение суммы элементов массива с индексом 2 и с индексом 4 равное 116. Как видно из примера, мы можем обращаться к любому элементу массива. А также вычислять необходимый номер элемента по различным формулам (например, как в программе A[i-1] или A[2*i], в данных случаях индексы элементов будут вычислены и зависят от значения i).

Разберем пример программы.
int N = 5;
int[] A = new int[N];
int x = 1;
A[x + 4] = A[x] + A[2 * (x + 1)];  // после подстановки х в выражения и вычислений 
                                  // получаем следующую строку A[5] = A[1] + A[4]
                                  // A[5] такого элемента не существует
                                  // ошибка - выход за границы массива

Массив объявлен из 5 элементов, значит, элементы будут иметь нумерацию от 0 до 4. Видим, что программа в 6й строке обращается к несуществующему элементу: A[5].
Получается, что программа вышла за границы массива.
Выход за границы массива - это обращение к элементу с индексом, который не существует в массиве.
В таких случая программа обычно завершается аварийно с ошибкой run-time error.

 

При работе с массивами обычно приходится работать сразу со всеми элементами массива.
Перебор элементов: просматриваем все элементы массива и, если нужно, выполняем с каждым из них некоторую операцию.
Для этого используется чаще всего цикл с переменной, которая изменяется от 0 до N-1, где N - количество элементом массива.
Под N будем считать текущий размер массива, то есть
N = A.Length;
...
for (int i = 0; i < N; i++)
{
     // здесь работаем с A[i] 
}
В указанном цикле переменная i будет принимать значения 0, 1, 2, ..., N-1.  Таким образом, на каждом шаге цикла мы обращаемся к конкретному элементу массива с номером i.
То есть достаточно описать, что нужно сделать с одним элементом массива A[i] и эти действия поместить внутрь такого цикла.

Напишем программу, которая заполняет массив первыми натуральными числами, то есть, по окончанию программы элементы массива должны стать равными
A[0] = 1
A[1] = 2
A[2] = 3
...
A[N - 1] = N
Нетрудно заметить закономерность: значение элемента массива должно быть больше на 1, чем индекс элемента.
Цикл будет выглядеть следующим образом
for (int i = 0; i < N; i++) { A[i] = i + 1; }

Кроме цикла for, так же можно использовать foreach - он преебирает все элементы массива, не запоминая их индексы. Иногда это может быть удобно, например, для вывода массива на экран.

foreach (int i in A)
        {
            Console.Write(i + " ");
        }


А вот так можно считать массив, элементы которого записаны в одной строке и разделены пробелом, с клавиатуры.
using System.Linq; // нужно прописать эту директиву, чтобы использовать функции,связанные с работой с массивами
...
string text = Console.ReadLine();
int[] array = text.Split(' ').Select(int.Parse).ToArray();
// Split() разделяет строку на отдельные объекты (в данном случае деление пробелом)
// Select(int.Parse) преобразует каждого объект (строку) в int
// ToArray() записывает все полученные объекты в массив array