Узнайте, как управлять коллекциями данных с помощью List<T> в C#
Это вводное руководство содержит общие сведения о языке C# и классе List<T>.
Предварительные требования
Для работы с руководством вам потребуется компьютер, настроенный для разработки в локальной среде. Инструкции по установке и общие сведения о разработке приложений в .NET см. в статье Настройка локальной среды .
Если вы предпочитаете выполнять код без настройки локальной среды, ознакомьтесь с интерактивной версией этого руководства в браузере.
Пример простого списка
Создайте каталог с именем list-tutorial. Откройте этот каталог и выполните команду dotnet new console
.
Важно!
В шаблонах C# для .NET 6 используются операторы верхнего уровня. Приложение может не соответствовать коду, приведенному в этой статье, если вы уже выполнили обновление до .NET 6. Дополнительные сведения см. в статье Новые шаблоны C# для создания инструкций верхнего уровня.
Пакет SDK для .NET 6 также добавляет набор неявныхglobal using
директив для проектов, использующих следующие пакеты SDK:
- Microsoft.NET.Sdk
- Microsoft.NET.Sdk.Web
- Microsoft.NET.Sdk.Worker
Эти неявные директивы global using
включают наиболее распространенные пространства имен для соответствующего типа проектов.
Дополнительные сведения см. в статье о директивах неявного использования.
Откройте Program.cs в любом редакторе и замените существующий код следующим:
List<string> names = ["<name>", "Ana", "Felipe"];
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
Замените <name>
собственным именем. Сохраните Program.cs. Введите в окне консоли команду dotnet run
для тестирования.
Вы создали список строк, добавили три имени в этот список и вывели имена прописными буквами. Для циклического прохода по списку вы примените концепции, которые изучили в предыдущих руководствах.
В коде для отображения имен используется функция интерполяции строк. Если перед string
добавить символ $
, код C# можно внедрять в объявление строки. Фактическая строка заменяет код C# генерируемым значением. В этом примере она заменяет {name.ToUpper()}
именами, буквы каждого из которых преобразованы в прописные, так как вызван метод ToUpper.
Продолжим изучение.
Изменение содержимого списка
В созданной коллекции используется тип List<T>. При применении такого типа сохраняются последовательности элементов. Тип элементов указывается в угловых скобках.
Важный аспект типа List<T> — возможность увеличения или уменьшения, что позволяет добавлять или удалять элементы. Добавьте этот код в конец программы:
Console.WriteLine();
names.Add("Maria");
names.Add("Bill");
names.Remove("Ana");
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
В конец списка добавлены еще два имени. При этом одно имя удалено. Сохраните файл и введите dotnet run
для тестирования.
List<T> позволяет добавлять ссылки на отдельные элементы по индексу. Поместите индекс между токенами [
и ]
после имени списка. Для первого индекса в C# используется значение 0. Добавьте следующий код сразу после добавленного фрагмента и протестируйте его:
Console.WriteLine($"My name is {names[0]}");
Console.WriteLine($"I've added {names[2]} and {names[3]} to the list");
Доступ к индексу за пределами списка получить невозможно. Помните, что индексы начинаются с 0, поэтому максимальный допустимый индекс меньше, чем число элементов в списке. Вы можете проверить, как долго в списке используется свойство Count. Добавьте следующий код в конец программы:
Console.WriteLine($"The list has {names.Count} people in it");
Сохраните файл и еще раз введите dotnet run
, чтобы просмотреть результаты.
Поиск по спискам и их сортировка
В наших примерах используются сравнительно небольшие списки. Но приложения часто создают списки с гораздо большим количеством элементов, иногда они исчисляются в тысячах. Чтобы найти элементы в таких больших коллекциях, необходимо выполнить поиск различных элементов по списку. Метод IndexOf выполняет поиск элемента и возвращает его индекс. Если элемент отсутствует в списке, IndexOf
возвращает -1
. Добавьте этот код в конец программы:
var index = names.IndexOf("Felipe");
if (index == -1)
{
Console.WriteLine($"When an item is not found, IndexOf returns {index}");
}
else
{
Console.WriteLine($"The name {names[index]} is at index {index}");
}
index = names.IndexOf("Not Found");
if (index == -1)
{
Console.WriteLine($"When an item is not found, IndexOf returns {index}");
}
else
{
Console.WriteLine($"The name {names[index]} is at index {index}");
}
Кроме того, можно сортировать элементы в списке. Метод Sort сортирует все элементы списка в обычном порядке (строки — в алфавитном). Добавьте этот код в конец программы:
names.Sort();
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
Сохраните файл и введите dotnet run
, чтобы протестировать последнюю версию.
Прежде чем перейти к следующему разделу, переместим текущий код в отдельный метод. Это упростит начало работы с новым примером. Поместите весь написанный код в новый метод с именем WorkWithStrings()
. Вызовите этот метод в начале кода программы. В результате ваш код должен выглядеть примерно следующим образом:
WorkWithStrings();
void WorkWithStrings()
{
List<string> names = ["<name>", "Ana", "Felipe"];
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
Console.WriteLine();
names.Add("Maria");
names.Add("Bill");
names.Remove("Ana");
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
Console.WriteLine($"My name is {names[0]}");
Console.WriteLine($"I've added {names[2]} and {names[3]} to the list");
Console.WriteLine($"The list has {names.Count} people in it");
var index = names.IndexOf("Felipe");
if (index == -1)
{
Console.WriteLine($"When an item is not found, IndexOf returns {index}");
}
else
{
Console.WriteLine($"The name {names[index]} is at index {index}");
}
index = names.IndexOf("Not Found");
if (index == -1)
{
Console.WriteLine($"When an item is not found, IndexOf returns {index}");
}
else
{
Console.WriteLine($"The name {names[index]} is at index {index}");
}
names.Sort();
foreach (var name in names)
{
Console.WriteLine($"Hello {name.ToUpper()}!");
}
}
Списки других типов
Вы уже использовали в списках тип string
. Создадим List<T> с использованием другого типа. Сначала создадим набор чисел.
Добавьте следующий код в программу после вызова WorkWithStrings()
:
List<int> fibonacciNumbers = [1, 1];
Будет создан список целых чисел. Для первых двух целых чисел будет задано значение 1. Это два первых значения последовательности Фибоначчи. Каждое следующее число Фибоначчи — это сумма двух предыдущих чисел. Добавьте этот код:
var previous = fibonacciNumbers[fibonacciNumbers.Count - 1];
var previous2 = fibonacciNumbers[fibonacciNumbers.Count - 2];
fibonacciNumbers.Add(previous + previous2);
foreach (var item in fibonacciNumbers)
{
Console.WriteLine(item);
}
Сохраните файл и введите dotnet run
, чтобы просмотреть результаты.
Совет
Для задач этого раздела вы можете закомментировать код, который вызывает WorkWithStrings();
. Просто поместите два /
символа перед вызовом, как показано ниже: // WorkWithStrings();
.
Задача
Попробуйте объединить некоторые идеи из этого и предыдущих занятий. Расширьте код с числами Фибоначчи, который вы создали. Попробуйте написать код для создания первых 20 чисел в последовательности. Подсказка: 20-е число Фибоначчи — 6765.
Выполнение задачи
Пример решения можно просмотреть в готовом примере кода на GitHub.
При каждой итерации цикла суммируются два последних целых числа в списке. Полученное значение добавляется в список. Цикл повторяется, пока в список не будут добавлены 20 элементов.
Поздравляем! Вы выполнили задачи в руководстве по спискам. Можете продолжить изучение дополнительных руководств в своей среде разработки.
Дополнительные сведения о работе с типом List
см. в статье Коллекции и структуры данных. Также в нем описаны многие другие типы коллекций.