Добавить в корзинуПозвонить
Найти в Дзене
UnderPlank

Практическое применение методов Substring и IndexOf в языках Си (C#)

Работа со строками — рутина, которая затрагивает буквально все сферы программирования. Думаю, многие сталкивались с тем, как неотлаженный алгоритм в прямом смысле "ломал" казалось бы рабочую схему обработки строк, а кому-то - и уверенность в собственных скиллах. Методы Substring и IndexOf позволяют эффективно решать задачи парсинга без использования регулярных выражений. Их комбинация дает гибкость: от простого извлечения данных до обработки вложенных структур. Однако важно учитывать пограничные случаи (например, отсутствие искомых символов) и добавлять проверки на -1 для IndexOf, чтобы избежать ошибок. Эти методы — отличная основа для работы с текстом в C#. Жизненный пример: Ошибка в маскировании номера карты из-за неправильного использования Substring и IndexOf
Представьте, что вы разрабатываете приложение для обработки платежей. Одна из задач — замаскировать номер кредитной карты, оставив только первые 4 и последние 4 цифры, например: "4111-1111-1111-1111" → "4111-****-****-1111".

Работа со строками — рутина, которая затрагивает буквально все сферы программирования. Думаю, многие сталкивались с тем, как неотлаженный алгоритм в прямом смысле "ломал" казалось бы рабочую схему обработки строк, а кому-то - и уверенность в собственных скиллах. Методы Substring и IndexOf позволяют эффективно решать задачи парсинга без использования регулярных выражений. Их комбинация дает гибкость: от простого извлечения данных до обработки вложенных структур. Однако важно учитывать пограничные случаи (например, отсутствие искомых символов) и добавлять проверки на -1 для IndexOf, чтобы избежать ошибок. Эти методы — отличная основа для работы с текстом в C#.

Жизненный пример: Ошибка в маскировании номера карты из-за неправильного использования Substring и IndexOf

Представьте, что вы разрабатываете приложение для обработки платежей. Одна из задач — замаскировать номер кредитной карты, оставив только первые 4 и последние 4 цифры, например: "4111-1111-1111-1111" → "4111-****-****-1111".
Для этого программист решает использовать IndexOf и Substring, но допускает критическую ошибку.

Код с ошибкой:

string cardNumber = "4111111111111111"; // Номер без дефисов
(пользователь ввёл данные неправильно)
int firstDash = cardNumber.IndexOf('-');
int lastDash = cardNumber.LastIndexOf('-');

// Попытка извлечь части номера:
string visiblePart = cardNumber.Substring(0, firstDash + 1); // Ожидается
"4111-"
string maskedPart = new string('*', lastDash - firstDash - 1);
string result = $"{visiblePart}{maskedPart}{cardNumber.Substring(lastDash)}";
Console.WriteLine(result);

Проблема:
Метод
IndexOf('-') вернет -1, так как дефисов в строке нет. Это приведет к:

  1. firstDash + 1 = 0, и Substring(0, 0) выбросит ArgumentOutOfRangeException.
  2. Даже если бы исключения не было, логика маскирования сломалась бы: вместо "4111****1111" получим неожиданный результат или ошибку.

Последствия:

  • Приложение крашится при обработке некорректных данных.
  • Если бы номер содержал дефисы в неожиданных местах (например, "41-11-1111111111"), маскирование стало бы частичным, случайно раскрыв часть цифр.

Исправленный подход:

  1. Всегда проверять результат IndexOf на -1.
  2. Учесть, что дефисы могут отсутствовать или находиться в произвольных позициях.
  3. Использовать универсальную логику для любого формата номера:

string cardNumber = "4111111111111111";
string maskedNumber = cardNumber.Length < 8
? cardNumber // Не маскируем слишком короткие номера
: $"{cardNumber.Substring(0, 4)}-****-****-
{cardNumber.Substring(cardNumber.Length - 4)}";
Console.WriteLine(maskedNumber); // Вывод: 4111-****-****-1111

Мораль:

Некорректное использование Substring и IndexOf без проверок может привести к утечке данных, ошибкам в работе приложения или его полному краху. Всегда:

  • Проверяйте результат IndexOf на -1.
  • Учитывайте возможность нестандартного формата входных данных.
  • Тестируйте edge-кейсы (пустые строки, отсутствие искомых символов, неожиданная длина строки).

-2

Еще курьезный пример: Ошибка в парсинге времени, превращающая «полночь» в «25 часов»

Представьте приложение для фитнеса, которое анализирует время тренировки. Пользователь вводит время в формате "ЧЧ:ММ:СС", но иногда забывает указать секунды. Программист решил обрабатывать это так:

string inputTime = "23:30"; // Пользователь ввёл только часы и минуты
int firstColon = inputTime.IndexOf(':'); // = 2
int secondColon = inputTime.IndexOf(':', firstColon + 1); // = -1 (второго
двоеточия нет!)

// Извлечение часов, минут, секунд:
int hours = int.Parse(inputTime.Substring(0, firstColon)); // 23
int minutes = int.Parse(inputTime.Substring(firstColon + 1, secondColon -
firstColon - 1)); // Ошибка: Substring(3, -4)
int seconds = int.Parse(inputTime.Substring(secondColon + 1)); // Substring(0) →
краш!
Console.WriteLine($"Время: {hours}:{minutes}:{seconds}");

Что произойдет:

  1. При попытке извлечь минуты Substring(3, -4) выбросит ArgumentOutOfRangeException, так как длина не может быть отрицательной.
  2. Если бы программист «пофиксил» это, подставив Math.Abs, минуты стали бы 30-(-4)-1=33, а секунды — 23:30 (из-за secondColon + 1 = 0).
  3. Результат: Время: 23:33:23:30 — словно тренировка длится 25 часов!

Почему это смешно (и опасно):

  • Пользователь увидит явный бред в статистике, но приложение не упадёт, а продолжит работать.
  • Если секунды рассчитываются как secondColon + 1, то Substring(0) вернет всю строку, и int.Parse("23:30") вызовет FormatException.

Как избежать:

  • Проверять secondColon на -1 перед использованием.
  • Использовать TimeSpan.Parse или регулярные выражения.


Неправильные проверки IndexOf и слепое доверие к Substring могут превратить ваше приложение в генератор абсурда. Всегда тестируйте эджкейсы!