Генерация строк и выполнение их как программ во время выполнения - PullRequest
1 голос
/ 11 апреля 2011

Это сложный вопрос к слову, и я не уверен, каким будет правильный термин для него (если таковой имеется). Мне любопытно, какие языки позволяют вам «строить» строку во время выполнения программы, а затем выполнять ее как часть программы. Единственный известный мне язык, который позволяет вам делать это, - это Снобол.

Однако, читая запись в Википедии для Tcl, звучит так, как будто она может сделать это тоже?

Я всегда думал, что это изящная функция, даже если ее не очень много используют. Спасибо.

PS: помечает это с помощью Snobol, Spitbol, ​​но не имеет репутации для создания новых тегов.

Ответы [ 3 ]

5 голосов
/ 11 апреля 2011

Мне любопытно, на каких языках можно «создать» строку во время выполнения программы, а затем выполнить ее как часть программы.

Ищите языки, которые поддерживают eval или, в более общем смысле, метапрограммирование во время выполнения .Практически каждый язык поддерживает eval (даже строго статически типизированные языки, такие как Haskell).Многие среды выполнения, созданные для языков, которые в основном реализуются с помощью интерпретации байт-кода (например, Lisp-подобные языки, Erlang или Java), поддерживают возможность вставки нового (байтового) кода во время выполнения.После того, как вы можете вставить новый код динамически, вы можете написать eval или выполнить «обезьянье патчирование».

Даже в языковых реализациях без специальной поддержки полного метапрограммирования или даже динамического связывания часто есть способыдля динамического генерирования кода под управлением программиста, либо с помощью механизмов отражения, либо с помощью библиотек поддержки генерации кода (таких как LLVM).

Помимо простого одноэтапного eval, в более общем смысле, языков, которые поддерживают многократные Этап Вычисления позволяют генерировать программы от одного этапа к другому для произвольного числа этапов, что позволяет безопасно, произвольно вкладывать evals.

По словам Тахи, который диссертацию по многоэтапному программированию модели представляет большую часть теории.

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

Языки, которые вы ищете, обычно предоставляют три примитива в той или иной форме:

  • задержка
  • сращивание
  • run

для задержки вычисления на один этап (например, цитирование фрагмента в виде строки), сращивание егов работающую программу и выполнение этого фрагмента (в Лиспе, обратная кавычка, запятая и eval).

Lisp и eval

Обобщение eval для многоступенчатого программирования

О многоступенчатом программировании:

  • Таха, Многоступенчатое программирование: его теория и приложения
  • Нильсон, Флемминг и Нильсон, Ханне Риис, Двухуровневые функциональные языки, - введены двухуровневые языки.
  • Таха, Валид и Шеард, Тим, Многоступенчатое программирование с явными аннотациями - простые операторы, поддерживающие все методы метапрограммирования во время выполнения.

Предоставление типов для многоступенчатого программирования

Формальные описания многоступенчатых вычислений довольно сложны и включают необычные методы (для языков программирования), такие как модальная логика.

Предоставление типов метапрограммам:

  • Виклайн, Филип и Ли, Питер и Пфеннинг, Фрэнк и Дэвис, Роуэн, Модальные типы в качестве промежуточных спецификаций для генерации кода во время выполнения.

Проблемы безопасности

Хитрость формализации семантики многоступенчатого программирования объясняет, почему они часто путают системы, с которыми приходится работать, и почему eval может открыть столько проблем с безопасностью: становится неясно, какой код выполняется, когда и какие именно данные используются.превращается в код.Перехват имен с одного этапа на другой довольно сложен, что приводит к атакам с использованием кода.Такая сложность не помогает безопасности.

3 голосов
/ 11 апреля 2011

Это можно сделать на всех диалектах Лисп, где эта функция возникла под именем eval, а также на прологе (call/1) и на любом количестве других языков. Большинство сохраняют имя eval, а большинство - динамические языки .

Как говорится, это едва ли изящная функция . Я бы назвал это серьезной проблемой безопасности, учитывая, насколько легко злоупотреблять этой функцией. Если вам нужно динамическое выполнение кода, то написание собственного, ограниченного микропереводчика (или использование чего-то вроде Lua) почти всегда является лучшей идеей.

3 голосов
/ 11 апреля 2011

Определенно может быть сделано на многих интерпретируемых языках сценариев. И некоторые языки специально разработаны для этого. Это может быть сделано, насколько мне известно, в:

  • Perl
  • PHP
  • Lisp (и диалекты, такие как CL, Clojure, Scheme и т. Д.)
  • JavaScript
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...