LINUX.ORG.RU

История изменений

Исправление X512, (текущая версия) :

Посмотрел я на Оберон…

Вы забыли главное преимущество: безопасность языка и наличие сборщика мусора. Все варианты Паскаля принципиально не сильно лучше C/C++, в них легко испортить память и сделать утечку памяти или double free. Есть 2 подхода обеспечения безопасности памяти: сборщик мусора как в Обероне и Go или контроль владения как в Rust. Rust слишком сложный, содержит недостатки и дыры в архитектуре и медленно компилируется, в нём нет нормальных модулей (динамическая загрузка, инициализаторы/финализаторы модулей, детерминированный порядок инициализации).

Где-то на уровне C++ (1983) и Standard ML (1984) это превосходство заканчивается, потому что они привносят высокий уровень полиморфизма с малыми накладными расходами.

В Обероне dynamic_cast эффективнее, чем в C++. Типичной практикой является обработка сообщений через проверку расширений типов:

PROCEDURE (c: Controller) HandleCtrlMsg* (
	f: Views.Frame; VAR msg: Controllers.Message; VAR focus: Views.View
), NEW, EXTENSIBLE;
BEGIN
	focus := c.focus;
	WITH msg: Controllers.PollCursorMsg DO
		PollCursor(c, f, msg, focus)
	| msg: Controllers.PollOpsMsg DO
		PollOps(c, f, msg, focus)
	| msg: PollFocusMsg DO
		IF msg.all OR (c.opts * modeOpts # mask) & (c.focus # NIL) THEN msg.ctrl := c END
	| msg: Controllers.TrackMsg DO
		Track(c, f, msg, focus)
	| msg: Controllers.EditMsg DO
		Edit(c, f, msg, focus)
	| msg: Controllers.TransferMessage DO
		Transfer(c, f, msg, focus)
	| msg: Controllers.SelectMsg DO
		IF focus = NIL THEN c.SelectAll(msg.set) END
	| msg: Controllers.TickMsg DO
		FadeMarks(c, show);
		CheckMaskFocus(c, f, focus)
	| msg: Controllers.MarkMsg DO
		c.bVis := msg.show;
		c.Mark(f, f.l, f.t, f.r, f.b, msg.show)
	| msg: Controllers.ReplaceViewMsg DO
		ReplaceView(c, msg.old, msg.new)
	| msg: Properties.CollectMsg DO
		IF focus = NIL THEN
			msg.poll.prop := ThisProp(c, direct)
		END
	| msg: Properties.EmitMsg DO
		IF focus = NIL THEN
			SetProp(c, msg.set.old, msg.set.prop, direct)
		END
	ELSE
	END
END HandleCtrlMsg;

В C++ аналогичный код будет страшно выглядеть и медленнее работать.

а в 1991 году выпускается Oberon-2, в который безальтернативно прошиты числа и строки без намека на перспективу.

Не понял что вы имеете в виду.

без намека на перспективу

В Component Pascal - наследнике Oberon 2 есть 4 числовых типа (BYTE, SHORTINT, INTEGER, LONGINT, 1, 2, 4 и 8 байт соответственно), а также 2 символьных типа SHORTCHAR (1 байт), CHAR (2 байта). Язык ничего не знает о кодировке кроме того, что во встроенных строковых операциях массив из символов должен оканчиваться на нулевой символ. Обработка кодировок выполняется в библиотеках.

Писать системщину на Oberon-2 можно, как и на Си, как и на паскале — но это тупо неэффективно.

Очень даже эффективно: не надо бороться с порчей памяти и нарушением консистентности указателей. Любой сколь-нибудь сложный код на Си/C++ полон багов и уязвимостей, позволяющих осуществить удалённое выполнение кода.

Исходная версия X512, :

Посмотрел я на Оберон…

Вы забыли главное преимущество: безопасность языка и наличие сборщика мусора. Все варианты Паскаля принципиально не сильно лучше C/C++, в них легко испортить память и сделать утечку памяти или double free. Есть 2 подхода обеспечения безопасности памяти: сборщик мусора как в Обероне и Go или контроль владения как в Rust.

Где-то на уровне C++ (1983) и Standard ML (1984) это превосходство заканчивается, потому что они привносят высокий уровень полиморфизма с малыми накладными расходами.

В Обероне dynamic_cast эффективнее, чем в C++. Типичной практикой является обработка сообщений через проверку расширений типов:

PROCEDURE (c: Controller) HandleCtrlMsg* (
	f: Views.Frame; VAR msg: Controllers.Message; VAR focus: Views.View
), NEW, EXTENSIBLE;
BEGIN
	focus := c.focus;
	WITH msg: Controllers.PollCursorMsg DO
		PollCursor(c, f, msg, focus)
	| msg: Controllers.PollOpsMsg DO
		PollOps(c, f, msg, focus)
	| msg: PollFocusMsg DO
		IF msg.all OR (c.opts * modeOpts # mask) & (c.focus # NIL) THEN msg.ctrl := c END
	| msg: Controllers.TrackMsg DO
		Track(c, f, msg, focus)
	| msg: Controllers.EditMsg DO
		Edit(c, f, msg, focus)
	| msg: Controllers.TransferMessage DO
		Transfer(c, f, msg, focus)
	| msg: Controllers.SelectMsg DO
		IF focus = NIL THEN c.SelectAll(msg.set) END
	| msg: Controllers.TickMsg DO
		FadeMarks(c, show);
		CheckMaskFocus(c, f, focus)
	| msg: Controllers.MarkMsg DO
		c.bVis := msg.show;
		c.Mark(f, f.l, f.t, f.r, f.b, msg.show)
	| msg: Controllers.ReplaceViewMsg DO
		ReplaceView(c, msg.old, msg.new)
	| msg: Properties.CollectMsg DO
		IF focus = NIL THEN
			msg.poll.prop := ThisProp(c, direct)
		END
	| msg: Properties.EmitMsg DO
		IF focus = NIL THEN
			SetProp(c, msg.set.old, msg.set.prop, direct)
		END
	ELSE
	END
END HandleCtrlMsg;

В C++ аналогичный код будет страшно выглядеть и медленнее работать.

а в 1991 году выпускается Oberon-2, в который безальтернативно прошиты числа и строки без намека на перспективу.

Не понял что вы имеете в виду.

без намека на перспективу

В Component Pascal - наследнике Oberon 2 есть 4 числовых типа (BYTE, SHORTINT, INTEGER, LONGINT, 1, 2, 4 и 8 байт соответственно), а также 2 символьных типа SHORTCHAR (1 байт), CHAR (2 байта). Язык ничего не знает о кодировке кроме того, что во встроенных строковых операциях массив из символов должен оканчиваться на нулевой символ. Обработка кодировок выполняется в библиотеках.

Писать системщину на Oberon-2 можно, как и на Си, как и на паскале — но это тупо неэффективно.

Очень даже эффективно: не надо бороться с порчей памяти и нарушением консистентности указателей. Любой сколь-нибудь сложный код на Си/C++ полон багов и уязвимостей, позволяющих осуществить удалённое выполнение кода.