Ответ
Runtime error (ошибка времени выполнения) — это исключение, которое возникает во время исполнения программы, когда синтаксически корректный код приводит к недопустимой операции. В отличие от ошибок компиляции, компилятор не может их обнаружить на этапе сборки.
Распространённые примеры исключений времени выполнения в .NET:
NullReferenceException: Попытка обращения к члену объекта, который равенnull.IndexOutOfRangeException: Попытка доступа к элементу массива или коллекции по индексу за её пределами.DivideByZeroException: Деление целочисленного значения на ноль.InvalidCastException: Неудачное приведение типа во время выполнения.StackOverflowException: Бесконечная рекурсия, исчерпавшая стек вызовов.OutOfMemoryException: Нехватка доступной памяти для выделения нового объекта.
Пример кода, вызывающего ошибку времени выполнения:
int[] numbers = { 1, 2, 3 };
Console.WriteLine(numbers[5]); // IndexOutOfRangeException
Обработка ошибок времени выполнения:
Для обработки таких ситуаций и предотвращения аварийного завершения программы используется конструкция try-catch-finally.
try
{
int divisor = 0;
int result = 10 / divisor; // Потенциальный DivideByZeroException
}
catch (DivideByZeroException ex)
{
// Логируем и обрабатываем конкретную ошибку
Console.WriteLine($"Ошибка: {ex.Message}");
// Возвращаем значение по умолчанию или пробрасываем исключение выше
}
catch (Exception ex) // Общий обработчик для других исключений
{
Console.WriteLine($"Произошла непредвиденная ошибка: {ex.Message}");
}
finally
{
// Этот блок выполнится всегда, даже если было исключение
Console.WriteLine("Операция завершена (успешно или с ошибкой).");
}
Профилактика: Лучшая практика — предвосхищать возможные ошибки с помощью проверок (валидация входных данных, проверка на null, использование безопасных операторов как ?. и ??).
Ответ 18+ 🔞
Давай разжую тебе про ошибки времени выполнения, а то я смотрю, народ путает их с чем попало. Это не те ошибки, которые компилятор ловит, когда ты код пишешь. Нет, блядь. Это та самая подстава, которая вылезает, когда программа уже запущена и вроде бы работает, а потом — бац! — и ты в консоли видишь красную хуйню, а пользователь — синий экран смерти.
Представь, ты написал код, скомпилировал — всё чисто, синтаксис идеальный. Запускаешь, а он тебе как даст: «На ноль делить нельзя, мудила!». Это и есть Runtime error. Компилятор-то не знал, что в переменной divisor окажется ноль, он видел просто переменную. А вот когда дело дошло до дела — пиздец.
Самые популярные грабли, на которые наступают все:
NullReferenceException— классика жанра. Пытаешься что-то сделать с объектом, а онnull. Как будто звонишь другу, а на том конце тишина и трубку не берут. «Вызови метод у этого объекта!» — «А у какого, сука? Его же нет!».IndexOutOfRangeException— ещё одна любимица. Массив на три элемента, а ты лезешь за пятым. Это как в очереди из трёх человек спросить: «Эй, пятый, ты чё стоишь?». Тебе сразу в еблет дадут, то есть исключение кинут.DivideByZeroException— тут всё ясно. Математика, 6 класс. Делить на ноль нельзя. А ты взял и поделил. Ну и какого хуя ты ожидал?InvalidCastException— решил, что в переменнойobjectлежит строка, а там на самом деле число. Попытался привести — получи по ебалу. Это как пытаться надеть трусы на голову и назвать это шапкой. Не катит.StackOverflowException— это когда метод вызывает сам себя, а тот вызывает себя, и так до бесконечности. Память для вызовов (стек) кончается, и всё, пиздец, приехали. Рекурсия без условия выхода — верный путь в ад.OutOfMemoryException— программа так захавала памяти, что системе больше нечего дать. Создавал объекты в цикле и забыл их удалять? Жди эту гостью.
Вот, смотри, как просто устроить катастрофу:
int[] numbers = { 1, 2, 3 };
Console.WriteLine(numbers[5]); // IndexOutOfRangeException
Всё. Программа аварийно завершится. Пользователь в панике.
Что делать, чтобы не выглядеть идиотом? Ловить эти ошибки!
Для этого есть try-catch-finally. Это как страховочная сетка под канатоходцем.
try
{
// Здесь мы идём по канату без страховки. Опасный код.
int divisor = 0;
int result = 10 / divisor; // Потенциальный DivideByZeroException
}
catch (DivideByZeroException ex) // Ловим конкретно деление на ноль
{
// Всё, поймали. Не упали, а мягко приземлились в эту секцию.
Console.WriteLine($"Ошибка: {ex.Message}");
// Тут можно сказать: «Сорян, на ноль делить нельзя, давай по-другому».
}
catch (Exception ex) // А это общая сетка. Сюда упадёт ВСЁ, что не поймали выше.
{
Console.WriteLine($"Произошла непредвиденная хуйня: {ex.Message}");
}
finally
{
// Этот блок выполнится ВСЕГДА. Упал ты или нет. Без вариантов.
// Типа, «операция завершена, можно убирать инструменты».
Console.WriteLine("Операция завершена (успешно или с ошибкой).");
}
Но лучшая стратегия — не допускать этого вообще!
Не надейся только на try-catch. Это как лечить болезнь, а не предотвращать её. Золотое правило:
- Проверяй на
null, прежде чем использовать объект. Или используй?.(null-условный оператор). - Смотри, не вылезаешь ли за границы массива.
- Проверяй знаменатель перед делением.
- Для приведения типов используй
asилиis, а не голый(Type).
Короче, думай головой, что может пойти не так, и предусматривай это. А try-catch — это уже последний рубеж обороны, когда всё пошло по пизде и нужно хоть как-то сохранить лицо и логи.