Неопределённое поведение

Неопределённое поведение

Неопределённое поведение (англ. undefined behaviour) — свойство некоторых языков программирования (наиболее заметно в Си), программных библиотек и аппаратного обеспечения в определённых маргинальных ситуациях выдавать результат, зависящий от реализации компилятора (библиотеки, микросхемы) и случайных параметров наподобие состояния памяти или сработавшего прерывания. Другими словами, спецификация не определяет поведение языка (библиотеки, микросхемы) в любых возможных ситуациях, а говорит: «при условии А результат операции Б не определён». Допускать такую ситуацию в программе считается ошибкой; даже если на некотором компиляторе программа успешно выполняется, она не будет кроссплатформенной и может отказать на другой машине, в другой ОС или при других настройках компилятора.

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

Содержание

Примеры

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

Большинство библиотек не проверяют указатели на NULL.

В процессорах x86, если есть два последовательных порта ввода-вывода и надо записать информацию сначала в один порт, потом в другой, это надо делать по одному байту: порядок прихода байтов на оборудование не гарантируется.

Ещё один пример неопределенного поведения: курьёз с ANSI-директивой «#pragma». Согласно спецификации языка компиляторам предоставлена полная свобода при обработке этой конструкции. До версии 1.17 компилятор GCC при нахождении в исходном коде этой директивы пытался запустить Emacs с игрой «Ханойские башни».

В качестве еще одного примера неопределенного поведения можно привести код:

int i = 5;
i = ++i + ++i;

При его выполнении переменная i может принять значения 13 или 14 для C/C++, 13 для Java, PHP и C#, 12 при реализации на LISP. Неопределенность в языке C/C++ связана с тем, что согласно стандартам С и С++ побочные эффекты (то есть инкремент в данном случае) могут быть применены в любой удобный для компилятора момент между двумя точками следования.

Достоинства

  • Определение некоторых операций как «неопределённых» приводит подобные языки (характеризующиеся зачастую отсутствием встроенной проверки на предел массива и т. д.) к упрощению спецификации и некоторому увеличению гибкости.
  • Ускоряется работа программ (так как не нужно проверять всевозможные «маргинальные» случаи).

Недостатки

  • Не гарантирует полной совместимости различных реализаций языка.
  • Недопущение ситуаций неопределённого поведения остаётся за программистом.

Ссылки



Wikimedia Foundation. 2010.

Игры ⚽ Нужен реферат?

Полезное


Смотреть что такое "Неопределённое поведение" в других словарях:

  • Неопределенное поведение — Неопределённое поведение (англ. Undefined behaviour)  свойство некоторых языков программирования (наиболее заметно в C) в определённых маргинальных ситуациях выдавать результат, зависящий от реализации компилятора. Другими словами, спецификация… …   Википедия

  • Неопределённостей соотношение — Квантовая механика Принцип неопределённости Введение ... Математическая формулировка ... Основа …   Википедия

  • Неопределённость Гейзенберга — Квантовая механика Принцип неопределённости Введение ... Математическая формулировка ... Основа …   Википедия

  • Printf — printf  обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода  вывода в различные потоки …   Википедия

  • Snprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия

  • Sprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия

  • Swprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия

  • Vasprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия

  • Vfprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия

  • Vsprintf — printf обобщённое название семейства функций или методов стандартных или широкоизвестных коммерческих библиотек, или встроенных операторов некоторых языков программирования, используемых для форматного вывода вывода в различные потоки значений… …   Википедия


Поделиться ссылкой на выделенное

Прямая ссылка:
Нажмите правой клавишей мыши и выберите «Копировать ссылку»