Работа с циклическими зависимостями в OCaml

StackOverflow https://stackoverflow.com/questions/36260

  •  09-06-2019
  •  | 
  •  

Вопрос

Я пишу интерпретатор для экспериментального языка.Тремя основными конструкциями языка являются определения, утверждения и выражения.Определения могут содержать инструкции и выражения, инструкции могут содержать определения и выражения, и один вид выражения может содержать инструкции.Я представляю все это с помощью типов объединения, поэтому могу легко использовать для них сопоставление с образцом.В идеале я хотел бы поместить код для них в разные файлы, но OMake жалуется на проблемы с циклическими зависимостями.Насколько я знаю, циклические определения типов между модулями не допускаются.

Единственный известный мне способ решить эту проблему - определить все три типа одновременно:

type defn = ...
and stmt = ...
and expr = ...

Похоже, для этого требуется, чтобы весь код для типов находился в одном файле.Есть ли какой-нибудь способ обойти это?Как вы справляетесь с циклическими определениями в своем коде?

Это было полезно?

Решение

Рекурсивные определения должны появляться в одном файле. Если вы хотите разделить определения, операторы и выражения в отдельные модули, вы можете сделать это, используя рекурсивные модули , но они все равно должны появиться в одном файле. Межфайловые зависимости между DAG-файлами - одна из неприятностей OCaml.

Другие советы

Это легко решается путем параметризации ваших типов по тем типам, на которые они ссылаются:

type ('stmt, 'expr) defn = ...
type ('defn, 'expr) stmt = ...
type ('defn, 'stmt) expr = ...

Этот метод называется "развязывание рекурсивного узла" (по отношению к гордиеву узлу) и был описан в Журнал OCaml Статья.

Ваше здоровье, Джон Харроп.

Другое часто используемое решение - абстрагирование типов в интерфейсах. Поскольку типы являются абстрактными в интерфейсах, эти интерфейсы не являются рекурсивно зависимыми. В реализациях вы можете указать типы, и поскольку реализации зависят только от интерфейсов, они также не являются рекурсивными.

Единственная проблема заключается в том, что с этим решением вы больше не сможете сопоставлять шаблоны для этих типов за пределами их реализации.

Лично, но это, вероятно, дело вкуса, мне нравится, когда все типы моей программы определены в одном модуле (я думаю, что это помогает в удобочитаемости программы). Таким образом, это ограничение OCaml не является для меня проблемой.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top