- PVSM.RU - https://www.pvsm.ru -

Umka. Жизнь статической типизации в скриптовом языке

Umka. Жизнь статической типизации в скриптовом языке - 1

В своё время посты на Хабре [1] и Reddit [2] о статически типизированном скриптовом языке Umka [3] вызвали весьма активную дискуссию.

Прошедшие полтора месяца позволили мне избавиться от некоторых заблуждений, развить язык и дать чуть более вразумительные ответы на вопросы публики. Как и следовало ожидать, наиболее серьёзное испытание выпало на долю самой концепции статической типизации. Она осталась в основе языка, но потребовала компромиссов — в частности, для корректной сборки мусора.

Появились первые замеры быстродействия интерпретатора в сравнении с Wren и Python — их результаты внушают оптимизм. Наконец, родился более реалистичный пример использования Umka по его основному назначению, т. е. как встраиваемого языка.

Информация о типах во время исполнения программы (RTTI). Проект начинался с радикального отказа от хранения типов данных при исполнении программы. Вся информация о типах терялась после компиляции в байт-код виртуальной машины. В принципе, статическая типизация позволяет это сделать, а заодно избавляет от странных трюков вроде упаковки данных в NaN [4], к которой, например, прибегают создатели JavaScript и Wren ради увеличения быстродействия. Однако обнаружились два случая, в которых пришлось использовать RTTI:

  • Приведение интерфейсного типа данных к конкретному — прямой аналог «утверждения типа» (type assertion) в Go, а также, отчасти, оператора dynamic_cast в C++. Оно требуется и при сборке мусора, содержащегося в данных, приведённых к интерфейсному типу.
  • Сборка мусора, связанного с динамическими структурами данных вроде списков и деревьев.

Быстродействие. Изначально Umka никак не предназначался для установления рекордов быстродействия. Безразличие публики к медлительности Python наводило на мысль, что скорость вовсе не то качество, которого в первую очередь ожидают от скриптового языка. Однако успех LuaJIT и активная реклама Wren заставили задуматься. После этого меня уже не удивляло, что и ранние публикации про Umka вызвали вопросы о быстродействии, хотя мне по-прежнему интересно, от кого в первую очередь исходит спрос на скорость. От разработчиков игр?

Пока полный набор тестов не готов, я могу поделиться лишь предварительными результатами замеров. В численных задачах (например, задаче многих тел) Umka надёжно опережает Python, а если в задаче активно используется цикл for, то Umka даёт выигрыш даже по сравнению с Wren, который позиционируется автором чуть ли не как самый быстрый скриптовый язык после LuaJIT. Наглядным примером служит перемножение больших матриц [5]:

Umka. Жизнь статической типизации в скриптовом языке - 2
Умножение матриц 400 x 400 (AMD A4-3300M @ 1.9 GHz, Windows 7)

Очевидно, в пользу Umka здесь сыграла поддержка традиционных статических массивов и более низкоуровневая организация цикла for, не содержащая вызовов методов.

Задачи с интенсивной сборкой мусора (например, создание и обход двоичных деревьев) вызывают много сомнений по поводу эквивалентности сравниваемых алгоритмов. Например, известная реализация двоичных деревьев на Python возвращает содержимое узлов россыпью [6] и выглядит так, будто в принципе допускает размещение всего дерева на стеке — вообще без использования кучи и сборки мусора. Однако она, по-видимому, требует динамической типизации и не может быть точно воспроизведена на Umka. Если же потребовать возвращать узлы в виде структур [7], как в Umka (а за неимением структур приходится требовать объекты), то быстродействие Python сразу же падает в 3-4 раза. Вариант на Umka [8] вдвое отстаёт от первой реализации и вдвое опережает вторую. Какое сравнение корректнее — не знаю.

Взаимодействие с внешним кодом. Коль скоро язык рассматривается как встраиваемый, понадобился более или менее реалистичный пример взаимодействия кода на C и Umka [9]. В нём средствами игровой библиотеки raylib [10] формируется трёхмерная сцена, а наполнение сцены определяется внешним скриптом на Umka. В примере можно найти и вызов функций Umka из кода на C, и вызов функций C из Umka. Статическая типизация языка Umka позволила естественным образом формировать на нём структуры данных, непосредственно воспринимаемые библиотекой raylib.

Umka. Жизнь статической типизации в скриптовом языке - 3
Пример трёхмерной сцены, содержимое которой задаётся скриптом на Umka

Обобщённые типы и функции (generics). Как только читатель улавливает сходство Umka с Go, пускай даже синтаксическое — следует вопрос о поддержке generic'ов. Работа в этом направлении пока не вышла из стадии обзора подходов. Конечно, хотелось бы воспользоваться предложениями разработчиков Go, однако сосуществование в их головах интерфейсов и «контрактов» всегда отпугивало, как странное дублирование понятий. К удивлению и радости, в только что вышедшей новой редакции черновика [11] «контракты» исчезли — по тем же причинам, о которых размышлял и я. Пока generic'ов в Umka нет, остаётся пользоваться, как и в Go, пустыми интерфейсами interface{}.

Документация. Полная спецификация Umka ещё в работе, но уже написана грамматика [12] и расширен обзорный тур [13] по основным возможностям языка.

Автор: Василий Терешков

Источник [14]


Сайт-источник PVSM.RU: https://www.pvsm.ru

Путь до страницы источника: https://www.pvsm.ru/programmirovanie/354238

Ссылки в тексте:

[1] Хабре: https://habr.com/ru/post/501002/

[2] Reddit: https://www.reddit.com/r/ProgrammingLanguages/comments/gf5w0p/umka_a_new_statically_typed_scripting_language/

[3] Umka: https://github.com/vtereshkov/umka-lang

[4] упаковки данных в NaN: http://wingolog.org/archives/2011/05/18/value-representation-in-javascript-implementations

[5] перемножение больших матриц: https://github.com/vtereshkov/umka-lang/blob/master/benchmarks/matrices.um

[6] возвращает содержимое узлов россыпью: https://github.com/vtereshkov/umka-lang/blob/master/benchmarks/trees_nostruct.py

[7] возвращать узлы в виде структур: https://github.com/vtereshkov/umka-lang/blob/master/benchmarks/trees.py

[8] Вариант на Umka: https://github.com/vtereshkov/umka-lang/blob/master/benchmarks/trees.um

[9] пример взаимодействия кода на C и Umka: https://github.com/vtereshkov/umka-lang/blob/master/examples/3dcam.c

[10] raylib: https://www.raylib.com/

[11] новой редакции черновика: https://go.googlesource.com/proposal/+/refs/heads/master/design/go2draft-type-parameters.md

[12] грамматика: https://github.com/vtereshkov/umka-lang#language-grammar

[13] обзорный тур: https://github.com/vtereshkov/umka-lang#a-tour-of-umka

[14] Источник: https://habr.com/ru/post/507510/?utm_source=habrahabr&utm_medium=rss&utm_campaign=507510