Рубрика «exception handling»

Существуют различные способы обработки ошибок в языках программирования:

  • стандартные для многих языков исключения (Java, Scala и прочий JVM, python и многие другие)
  • коды статуса или флаги (Go, bash)
  • различные алгебраические структуры данных, значениями которых могут быть как успешные результаты так и описания ошибок (Scala, haskell и другие функциональные языки)

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

Последнее время я работаю со Scala, где в равной мере я могу использовать как исключения так и различные типы данных для обработки ошибок, поэтому интересно какой из подходов будет удобнее и быстрее.

Сразу отбросим использование кодов и флагов, так как этот подход не принят в JVM языках и по моему мнению слишком подвержен ошибкам (прошу прощения за каламбур). Поэтому будем сравнивать исключения и разные виды АТД. Кроме того АТД можно рассматривать как использование кодов ошибок в функциональном стиле.

UPDATE: к сравнению добавлены исключения без стек-трейсов

Читать полностью »

Странно, что на Хабре до сих пор не было упомянуто о наделавшем шуму предложении к стандарту C++ под названием "Zero-overhead deterministic exceptions". Исправляю это досадное упущение.

Если вас беспокоит оверхед исключений, или вам приходилось компилировать код без поддержки исключений, или просто интересно, что будет с исключениями в C++2b (отсылка к недавнему посту), прошу под кат. Вас ждёт выжимка из всего, что сейчас можно найти по теме, и пара опросов.

Читать полностью »

Недавно были опубликованы черновики дизайна новой обработки ошибок в Go 2. Очень радует, что язык не стоит на одном месте — он развивается и c каждым годом хорошеет как на дрожжах.

Только вот пока Go 2 лишь виднеется на горизонте, а ждать уж очень тягостно и грустно. Посему берем дело в свои руки. Немножко кодогенерации, чуть работы с ast, и легким движением руки паники превращаются, превращаются паники… в элегантные исключения!

Такой исключительный Go - 1

Читать полностью »

image

Предлагаю вашему вниманию перевод оригинальной статьи Роберта С. Мартина.

За последние несколько месяцев я попробовал два новых языка. Swift и Kotlin. У этих двух языков есть ряд общих особенностей. Действительно, сходство настолько сильное, что мне стало интересно, не является ли это новой тенденцией в нашей языкомешалке. Если это действительно так, то это тёмный путь.

Оба языка включают в себя некоторые функциональные характеристики. Например, в них обоих есть лямбды. В целом, это хорошая штука. Чем больше мы узнаем о функциональном программировании, тем лучше. Эти языки далеки от по-настоящему функционального языка программирования; но каждый шаг в этом направлении — хороший шаг.

Проблема в том, что оба языка сделали ставку на сильную статическую типизацию. Кажется, оба намерены заткнуть каждую дыру в своём родном языке. В случае со Swift – это странный гибрид C и Smalltalk, который называется Objective-C; поэтому, возможно, упор на типизацию понятен. Что касается Kotlin – его предком является уже довольно строго типизированная Java.

Я не хочу, чтобы вы думали, что я против статически типизированных языков. Я не против. Есть определенные преимущества как для динамических, так и для статических языков; и я с удовольствием пользуюсь обоими видами. Я предпочитаю динамическую типизацию, и поэтому я иногда использую Clojure. С другой стороны, я, вероятно, пишу больше Java, чем Clojure. Поэтому вы можете считать меня би-типичным. Я иду по обеим сторонам улицы — если так можно выразиться.

Дело не в том, что меня беспокоит, что Swift и Kotlin статически типизированы. Скорее меня беспокоит глубина статической типизации.Читать полностью »

image

При разработке приложений часто приходится сталкиваться с необходимостью просмотра вывода exception stack trace (в логах или при debug-инге). Хотелось бы иметь возможность автоматически попадать в необходимое место кода, прямо кликом по строке в выводе stack trace в браузере или в терминале.

Если вы являетесь пользователем одного из последних продуктов компании JetBrains (в частности PhpStorm), вы можете использовать для этих целей внутреннее REST API (для навигации из браузера) и command line launcher (для навигации в терминале).

Навигация в браузере

Частичное описание методов REST API IDE от JetBrains можно посмотреть здесь:

» http://develar.org/idea-rest-api/

Одним из методов этого API является возможность открыть файл проекта и переместиться на произвольную позицию в этом файле внутри самой IDE.

Читать полностью »

Сколько нужно времени, чтобы просто вывести на экран большой список, используя современные фреймворки?

Список на 2000 строк ReactJS AngularJS Raw HTML SAPUI5 $mol
Появление списка 170 ms 420 ms 260 ms 1200 ms 50 ms
Обновление всех его данных 75 ms 75 ms 260 ms 1200 ms 10 ms

Напишем нехитрое приложение — личный список задач. Какие у него будут характеристики?

ToDoMVC ReactJS AngularJS PolymerJS VanillaJS $mol
Размер ( html + js + css + templates ) * gzip 322 KB 326 KB 56 KB 20 KB 23 KB
Время загрузки 1.4 s 1.5 s 1.0 s 1.7 s 0.7 s
Время создания и удаления 100 задач 1.3 s 1.7 s 1.4 s 1.6 s 0.5s

Небольшая головоломка: перед вами синхронный код, загружающий и обрабатывающий содержимое 4 файлов, но с сервера они грузятся параллельно. Как такое может быть?

Синхронная параллельная загрузка ресурсов

А теперь прошу за мной в кроличью нору, настало время удивительных историй...

Читать полностью »

В сборках GCC под windows (cygwin,mingw) из коробки нет удобного макроса __try{} __except{} для перехвата как программных (throw MyExc) так и системных (сигналы). Попробуем изобрести свой велосипед.

Вся статья в 3-х пунктах:

  1. Создаём try catch блок
  2. Оборачиваем его в SEH блок
  3. Когда SEH поймает исключение, бросаем программное исключение

Если заинтересовал, добро пожаловать под кат.
Читать полностью »

Уже давно хотел поразбираться с анализаторами на основе Розлина. Тем более, что меня уже был опыт создания плагинов для Resharper-а (R# Contract Editor Extension), поэтому хотелось сравнить разные инфраструктуры и удобство использования. Есть идея переписать этот плагин с помощью анализаторов Roslyn-а, но я решил начать с чего-то попроще.

Цель недельного проекта была такая: сделать простой анализатор, который будет показывать типовые ошибки обработки исключений. Самые болезненные с моей точки зрения такие:

  • Повторная генерация исключений с помощью throw ex;
  • “Проглатывание” всех исключений с помощью пустых блоков catch {} или catch(Exception) {}.
  • “Проглатывание” исключений в определенных ветках блока catch.
  • Сохранение в логгах только сообщения ex.Message, теряя при этом потенциально важную информацию о месте возникновения исключения.
  • Некорректное пробрасывание новых исключений из блока catch.

Читать полностью »

Наверняка все знают прописную (в книгах про С++) истину о чудесной методологии RAII, если нет — приведу краткое описание из википедии.

Это шаблонное описание этой техники

Получение ресурса есть инициализация (англ. Resource Acquisition Is Initialization (RAII)) — программная идиома объектно-ориентированного программирования, смысл которой заключается в том, что с помощью тех или иных программных механизмов получение некоторого ресурса неразрывно совмещается с инициализацией, а освобождение — с уничтожением объекта.

Типичным (хотя и не единственным) способом реализации является организация получения доступа к ресурсу в конструкторе, а освобождения — в деструкторе соответствующего класса. Поскольку деструктор автоматической переменной вызывается при выходе её из области видимости, то ресурс гарантированно освобождается при уничтожении переменной. Это справедливо и в ситуациях, в которых возникают исключения. Это делает RAII ключевой концепцией для написания безопасного при исключениях кода в языках программирования, где конструкторы и деструкторы автоматических объектов вызываются автоматически, прежде всего — в C++.

Последнее предложение вроде как обещает 100% гарантию результата, но как всегда в жизни, а особенно в С++, есть ньюанс.
Читать полностью »

Rust LogoСегодня Аарон Тюрон — разработчик, недавно присоединившийся к разработке Rust в Mozilla — объявил об отсрочке реализации какого-либо механизма исключений, кроме уже существующего макроса try! и типа Result, до неопределённого момента после первого релиза языка программирования Rust.

Это означает, что в Rust 1.0 будут отсутствовать исключения первого класса — то есть, полностью интегрированные с другими фичами языка.

Для обработки ошибок в данной момент в Rust существует тип Result { Ok(value), Err(why) } и макрос try!. Тип Result представляет из себя перечисление (enum), похожее на Option { Some(value), None } и связанное с ним по смыслу. Вариант None типа Option говорит об отстутствии значения, а вариант Err(why) типа Result уточняет, почему значение отсутствует.

Rust предлагает возвращать тип Result из функций, чтобы передавать значение возврата или причину, по которой значение вернуть не удалось. Макрос try! в свою очередь позволяет автоматически возвращать Err(why) из текущей функции, если вызов другой функции не удался (применяется к объекту типа Result).
Читать полностью »