Интересно, что Вирт выкинул ident из case-меток и оставил только литерные константы integer и string (типа CHAR). Может он прислушался к
моей критике (в конце) и почитывает это форум? (или ему докладывают информаторы)
Основной вклад версии 25.02.2015, это оператор CASE понимаемый как WITH. Теперь использование CASE как старого CASE и CASE как WITH, определяется только на этапе
семантического анализа. Вот никогда не понимал этого стремления уменьшить число ключевых слов за счет их семантической перегрузки, очевидно, чтобы продемонстрировать очередное уменьшение сложности языка. Каждому терминалу должен быть сопоставлен единственный семантический смысл (тогда он будет ясен еще при синтаксическом анализе), притом, не зависящий от контекста, и тогда мы увидим подлинный объем
лексики языка. Сложность
синтаксиса можно оценить только через число его правил и подвыражений. А чтобы увидеть сложность
всего языка нужно полностью описать его семантику через контексто-зависимую аттрибутивную грамматику.
К тому же, как я уже говорил, я идеологически против изменения пространства имен внутри операторного блока, и поэтому против оператора WITH, у которого в разных секциях одна и та же переменная имеет разный тип. Динамические типы нужно реализовывать через абстрактные процедуры и модули, тип которых конкретизируется в момент вызова или загрузки.
Отличие первое: Вирт поменял определение типа SET, теперь это "SET the sets of integers between 0 and an implementation-dependent limit ", то есть SET может быть и 8 битным и 32 и 128 и даже 3 битным. Зависит от реализации.
Таким образом Вирт окончательно отвязал Оберон от 32битной платформы и мы теперь не знаем какая разрядность у INTEGER'a, SET и так далее.
Нет, это произошло еще в версии от 11 марта 2014 г. (Revision 10.03.2014-I)
Портабельность приложений написанных на Обероне становится довольно условной.
Для портабельности требуется ввести в каждый исходный файл версию компилятора (либо сигнатуру полностью конкретизированной во всех деталях версии языка), типа спецкомментария, и расширить компилятор на ее обработку. Модули разных версий (как исходники, так и бинарники) будут не совместимы и не смогут использоваться вместе. Прямой переносимости программ не будет, но можно сделать канонический транслятор исходников из версии в версию.
К сожалению в Обероне даже нельзя сделать TYPE INT16 = INTEGER -- это запрещено репортом. Можно конечно выкрутиться тестами и прочим, но это уже не просто костыли, это уже целые заросли костылей. Экзоскелет для оберона.
В Обероне-11 и позднее вообще невозможно во время компиляции проверить реализацию базовых типов, или определить реализацию в реал-тайм, даже поверить реализацию в реал-тайм можно только через аварийный выход. В более ранних версиях можно проверить реализацию во время компиляции посредством функций MIN, MAX и DIV.
(* all version: *)
(* MIN(LONGINT) <= MIN(INTEGER) *)
(* MIN(INTEGER) <= MIN(BYTE) *)
(* MIN(BYTE) <= MAX(BYTE) *)
(* MAX(BYTE) <= MAX(INTEGER) *)
(* MAX(INTEGER) <= MAX(LONGINT) *)
CONST
sheckminint = 1 DIV
MIN(
MIN(
(MIN(BYTE)+1) - MIN(MIN(BYTE)+1,-127-1),
MAX(MIN(BYTE),-127) - MIN(BYTE)
),
MIN(
(MIN(INTEGER)+1) - MIN(MIN(INTEGER),-2147483647-1),
MAX(MIN(INTEGER),-2147483647) - MIN(INTEGER)
),
MIN(
(MIN(LONGINT)+1) - MIN(MIN(LONGINT),-9223372036854775807-1),
MAX(MIN(LONGINT),-9223372036854775807) - MIN(LONGINT)
)
);
(* equivalent: *)
(* 1 <= MAX(LONGINT) *)
(* MIN(BYTE) = -128 *)
(* MIN(INTEGER) = -2147483648 *)
(* MIN(LONGINT) = -9223372036854775808 *)
CONST
sheckmaxint = 1 DIV
MIN(
MIN(
MAX(BYTE) - MIN(MAX(BYTE),127-1),
MAX(MAX(BYTE)-1,127) - (MAX(BYTE)-1)
),
MIN(
MAX(INTEGER) - MIN(MAX(INTEGER),2147483647-1),
MAX(MAX(INTEGER)-1,2147483647) - (MAX(INTEGER)-1)
),
MIN(
MAX(LONGINT) - MIN(MAX(LONGINT),9223372036854775807-1),
MAX(MAX(LONGINT)-1,9223372036854775807) - (MAX(LONGINT)-1)
)
);
(* equivalent: *)
(* MIN(LONGINT) <= 1 *)
(* MAX(BYTE) = 127 *)
(* MAX(INTEGER) = 2147483647 *)
(* MAX(LONGINT) = 9223372036854775807 *)