Мы тут продумываем дизайн параметризованных правил. В двух словах параметризованные правила — это правила которые имеют нечто вроде параметра типов, но вместо типа в него подставляется другое правило. Получается что-то вроде обобщенных правил.
Вот пример (из реальной грамматики JSON) демонстрирующий проблему решаемую параметризованными правилами:
Выделенное жирным правило StringLiteral2 практически дублирует правило StringLiteral1. Разница заключается только в типе кавычки заданной в подправиле Quote.
Бывают случае когда такое дублирование принимает угрожающие размеры. Например, в грамматике нового форматера РСДН таких мест довольно много Paragraph.nitra, Content.nitra. Правило Part, в каждом своем вхождении, дублирует один и тот же код.
Так вот возникла идея ввести параметризованные правила, чтобы избавиться от этого дублирования.
Вот пример приведенной выше грамматики литералов JSON-а переписанный с гипотетическими параметризованными правилами:
Так как Нитра является статически типизируемым языком, на параметры правил налагаются определенные ограничения. В приведенном примере в качестве параметра Quote можно подставить исключительно regex-правило, так как оно применяется в теле другого regex-правила. Могут быть следующие ограничения:
1. Параметр может быть исключительно regex-правилом.
2. Параметр может быть regex-правилом или token-правилом.
3. Параметр может быть любым правилом (т.е. regex, token или syntax).
В приведенном примере тип параметра выводится из использования, т.е. при компиляции компилятор узнает тип Quote только после того как проведет анализ всех (или части) подправил. Так как параметры правил это часть публичного интерфейса, то резонно возникают сомнения относительно целесообразности его вывода.
Альтернативой выводу типа параметров может быть явная его задание при объявлении параметра.
Например, так:
Собственно вопрос в том насколько интуитивным являются следующие соглашения
* regex — означает что правило может быть только regex-ом.
* token — правило может быть token-правилом или regex-ом.
* syntax — правило может быть syntax-правилом, token-правилом или regex-ом.
Не введет ли это пользователей в заблуждение?
Если это плохое решение, то предлагайте свои варианты, которые кажутся вам более интуитивными.
ЗЫ
Еще, возможно, будет разумно различать аннотации для расширяемых правил (или-правила) и для обычных. Тут уже совсем не ясно как это описать синтаксически. Если есть идеи, милости просим.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, btn1, Вы писали:
B>С этого момента непонятно PEG — он же вроде однородный, описал правило — получи соответствие! Зачем нужны типы для правил?
В Найтре давно не совсем PEG. На нижнем уровне используются классические регулярные выражения. Они быстрее и экономичнее по памяти.
Так же делается разделение на обычные правила и токены. Токены — это по сути обычные правила (в них доступна рекурсия), но в них не производится подстановка пробельных правил и они иначе интерпретируются при восстановлении и в IDE.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, VladD2, Вы писали:
s22>>Почему тогда не сделать параметризацией и константами? VD>Зачем?
За тем, что у нас вот такая хрень есть.
| UpperBound = "{" sm "," sm Number sm "}" { override Bounds = (0, Some(Number.Value())); }
| LowerBound = "{" sm Number "," sm "}" { override Bounds = (Number.Value(), None()); }
| FullBounds = "{" sm Number "," sm Number sm "}" { override Bounds = (Number1.Value(), Some(Number2.Value())); }
| Exact = "{" sm Number sm "}" { override Bounds { def x = Number.Value(); (x, Some(x)); } }
... << RSDN@Home 1.2.0 alpha 5 rev. 62>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Здравствуйте, VladD2, Вы писали:
WH>>За тем, что у нас вот такая хрень есть. VD>Не думаю, что в этом есть особый смысл. VD>В прочем, можно и числа поддержать.
Нам это почти ничего не стоит.
... << RSDN@Home 1.2.0 alpha 5 rev. 62>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Здравствуйте, VladD2, Вы писали:
VD>В приведенном примере тип параметра выводится из использования, т.е. при компиляции компилятор узнает тип Quote только после того как проведет анализ всех (или части) подправил. Так как параметры правил это часть публичного интерфейса, то резонно возникают сомнения относительно целесообразности его вывода.
Моё мнение задавать тип параметра правила нужно явно.
Ибо это публичный контракт правила.
Даже в языках, где вывод типов суров и глобален, правилом хорошего тона является явное задание типов функций, которые экспортируются из модуля.
... << RSDN@Home 1.2.0 alpha 5 rev. 62>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Здравствуйте, WolfHound, Вы писали:
WH>Здравствуйте, VladD2, Вы писали:
VD>>В приведенном примере тип параметра выводится из использования, т.е. при компиляции компилятор узнает тип Quote только после того как проведет анализ всех (или части) подправил. Так как параметры правил это часть публичного интерфейса, то резонно возникают сомнения относительно целесообразности его вывода. WH>Моё мнение задавать тип параметра правила нужно явно. WH>Ибо это публичный контракт правила. WH>Даже в языках, где вывод типов суров и глобален, правилом хорошего тона является явное задание типов функций, которые экспортируются из модуля.
Согласен.
Но как быть с тем, что синтаксис, токен и регексп не являются наследниками друг друга?
А есл метод может включать снтаксис то может включать регексп
Единственное сделать что то типа иерархии.
Здравствуйте, WolfHound, Вы писали:
WH>Здравствуйте, s22, Вы писали:
WH>>>Нам это почти ничего не стоит. s22>>А пробрасывать функции? (в методы обработки) WH>Не понял.
Здравствуйте, WolfHound, Вы писали:
WH>Моё мнение задавать тип параметра правила нужно явно.
Да я же не против. Цель этой темы придумать внятный синтаксис или подтвердить, что люди понимают предложенный. Пока что (судя по отсутствию осмысленных ответов) люди его не очень понимают. Даже наличие 3 сущностей кое-кого смущает. А уж указание token за regex явно будет смущать.
Народ! Высказывайтесь, плиз.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, VladD2, Вы писали:
VD>Да я же не против. Цель этой темы придумать внятный синтаксис или подтвердить, что люди понимают предложенный. Пока что (судя по отсутствию осмысленных ответов) люди его не очень понимают. Даже наличие 3 сущностей кое-кого смущает. А уж указание token за regex явно будет смущать.
У тебя будут ровно эти же сущности. Только они будут выводиться.
... << RSDN@Home 1.2.0 alpha 5 rev. 62>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Здравствуйте, VladD2, Вы писали:
VD>Здравствуйте, WolfHound, Вы писали:
WH>>Моё мнение задавать тип параметра правила нужно явно.
VD>Да я же не против. Цель этой темы придумать внятный синтаксис или подтвердить, что люди понимают предложенный. Пока что (судя по отсутствию осмысленных ответов) люди его не очень понимают. Даже наличие 3 сущностей кое-кого смущает. А уж указание token за regex явно будет смущать.
VD>Народ! Высказывайтесь, плиз.
Параметризированные правила хорошая вещь, но мое мнение, параметры типов не надо указывать, притом что это не параметры типов, они не говорят о конкретном правиле или типе, поэтому о типизации здесь речь не идет, сравнивая с обычными языками где есть контракт интерфейса на входные типы, существует всего три варианта подстановки и неужели эту работу выбрать токен, режекс или синтакс не может сделать компилятор за пользователя, которому эти лишние сложности, ключевые слова и ограничения не нужны, он просто пишет быстро грамматику, в наиболее короткой форме, компилятор все остальное делает сам. Параметры правил больше похожи на обобщенные типы где T в большинстве не описывается как определенная сущность, часто там может быть что угодно и при связывании уже метод вызывается со своим T, ограничения на T where T : class и тп делается редко и далеко не всегда, чаще используется обычный <T>. Можно сделать два синтаксиса как и есть в Н и C#, обобщенный <T> которому подставляется что угодно и компилятор найтры смотрит сопоставления при компиляции правила, также можно указать явно токен, режекс или синтакс правило которое может подставляться туда, и можно как публичный интерфейс задавать ограничения на правило, но для обычных проектов где краткость кода и удобство использования языка на главном месте, никакие лишние ключевые слова не нужны, в любом случае если правило переопределяется или используется из внешней библиотеки оно может проверяться при компиляции на соответствие также, как аналогично и с С# и остальными языками с обобщенными типами.
Здравствуйте, VladD2, Вы писали:
VD>Мы тут продумываем дизайн параметризованных правил. В двух словах параметризованные правила — это правила которые имеют нечто вроде параметра типов, но вместо типа в него подставляется другое правило. Получается что-то вроде обобщенных правил.
VD>Собственно вопрос в том насколько интуитивным являются следующие соглашения VD>* regex — означает что правило может быть только regex-ом. VD>* token — правило может быть token-правилом или regex-ом. VD>* syntax — правило может быть syntax-правилом, token-правилом или regex-ом.
Мне кажется, это будет сбивать с толку. Лучше ввести другие ключевые слова.
Еще мне не очень нравятся угловые скобки. Лучше обычные. Оно как то логичнее на мой взгляд, получится.
Угловые скобки банально привычнее для людей. Плюс круглые скобки уж используются в грамматике (внутри правил), так что будет конфликт.
_>А вообще с введением параметров, напрашиваются управляющие конструкции обрабатывающие входные параметры, что то типа :
Эти параметры не препроцессорные символы. Скорее их можно сравнить со ссылками на функции. Параметризованные правила (скорее всего) будут доступны в бинарном виде из внешних сборок (как дженерики или функции).
Так что управлять генерацией кода в них будет нельзя.
Зато у нас и так есть средства расширения — extend.
Список правил можно даже в рантайме изменять. Как минимум мы хотим воспроивести поведение Немерла в котором можно расширять грамматику с помощью using-а (импорта).
Параметризованные же правила — это некий вариант обобщений. Но они будут не шаблонного (шаблонов С++) плана, а скорее более похожими на дженерики дотнета или даже на функции высшего порядка. По сути правила — это функции. Так что для того чтобы передать правилу ссылку на другое правило, нужно просто передать ему ссылку на функцию или некий интерфейс.
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Если я правильно понял, тип параметра определяется описанием правила, а не объявлением параметра. Для меня важным является описание правила. И если объявление типа конфликтует с описанием правила, тогда я не хочу заморачиваться с объявлением типа.
Здравствуйте, Рамиль Вахитов, Вы писали:
РВ>Если я правильно понял, тип параметра определяется описанием правила, а не объявлением параметра. Для меня важным является описание правила. И если объявление типа конфликтует с описанием правила, тогда я не хочу заморачиваться с объявлением типа.
Не правильно.
Тип у параметра будет и так и так.
Вопрос в том указывать явно или выводить.
... << RSDN@Home 1.2.0 alpha 5 rev. 62>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн