Проверка порядка элаборации
В некоторых языках программирования, которые подразумевают наличие аналогичных проблем элаборации (например Java и C++), программист вынужден заботиться о порядке элаборации самостоятельно.
В следствие этого, часто встречаются случаи написания программ в которых выбор неправильного порядка элаборации приводит к неожиданным результатам, поскольку при этом используются переменные, значения которых не инициализированы.
Язык Ада был разработан как надежный язык и заботы программиста о порядке элаборации не так значительны.
В результате, язык предусматривает три уровня защиты:
Стандартные правила элаборации
накладывают некоторые ограничения на выбор порядка элаборации.
В частности, если какой-либо модуль указан в спецификаторе with, то элаборация его спецификации всегда осуществляется перед элаборацией модуля, который содержит этот спецификатор with.
Подобным образом, элаборация спецификации модуля-предка всегда осуществляется перед элаборацией спецификации модуля-потомка, и, в заключение, элаборация спецификации всегда осуществляется перед элаборацией соответствующего тела.
Динамические проверки элаборации
осуществляются во время выполнения программы.
Таким образом, если доступ к какой-либо сущности осуществляется до ее элаборации (обычно это происходит при вызовах подпрограмм), то возбуждается исключение Program_Error.
Средства управления элаборацией
позволяют программисту явно указывать необходимый порядок элаборации.
Рассмотрим перечисленные возможности более детально.
Во-первых, правила динамической проверки.
Одно из правил заключается в том, что при попытке использования переменной, элаборация которой не была выполнена, возбуждается исключение Program_Error.
Недостатком такого подхода является то, что затраты производительности на проверку каждой переменной могут оказаться достаточно дорогостоящими.
Вместо этого, Ada95 поддерживает два несколько более строгих правила, соблюдение которых легко проверить:
Такое правило гарантирует, что элаборация спецификации подпрограммы будет выполнена перед вызовом подпрограммы, а не перед элаборацией тела.
При нарушении этого правила возбуждается исключение Program_Error.
Такое правило гарантирует, что элаборация спецификации настраиваемого модуля будет выполнена перед конкретизацией настраиваемого модуля, а не перед элаборацией тела.
При нарушении этого правила возбуждается исключение Program_Error.
Смысл идеи заключается в том, что при осуществлении элаборации тела элаборация любых переменных, которые используются в этом теле, должна быть уже выполнена.
Таким образом, при проверке элаборации тела гарантируется, что ни один из ресурсов, которые использует это тело, не окажется источником каких-либо неожиданностей.
Как было замечено ранее, такие правила несколько более строгие, поскольку необходима гарантия корректности вызова подпрограммы, которая использует в своем теле не локальные для этой подпрограммы ресурсы.
Однако, полностью полагаться на эти правила будет не безопасно, поскольку это подразумевает, что вызывающая подпрограмма должна заботится о деталях реализации, которые размещенны в теле, что противоречит основным принципам Ады.
Вероятная реализация такой идеи может выглядеть следующим образом.
С каждой подпрограммой и с каждым настраиваемым модулем может быть ассоциирована логическая переменная.
Первоначально такая переменная имеет значение "ложь" (False), а после осуществления элаборации тела эта переменная устанавливается в значение "истина" (True).
Проверка значения этой переменной выполняется при осуществлении вызова или конкретизации, и когда значение переменной - "ложь" (False), возбуждается исключение Program_Error.