2012-04-25 3 views
2

Я кодирую проект на C++, и я ищу способ вставить текстовый файл (usergrammar.txt) в удобочитаемую/записываемую форму, определяемую пользователем грамматику, которая определяет объекты.Загрузить грамматику во время выполнения

После этого я хотел бы иметь возможность указать некоторые из этих объектов в коде и сохранить созданные экземпляры в другом файле (instance.txt), всегда в доступном для людей формате. Этот второй файл, очевидно, зависит от того, что первое должно быть правильно прочитано.

У меня возникли проблемы с тем, как определить грамматику и разобрать их. Я смотрел на Boost :: Spirit, но пока он хорошо справляется с чтением первого файла (поскольку его правила предопределены), я не думаю, что он применим ко второму, поскольку только грамматические символы Spirit время компиляции и не может быть загружено во время выполнения (по крайней мере, это то, что я понял).

Теперь я читаю о форме ENBF, но у меня также есть проблема, что у меня есть не только языковые правила, но каждый объект имеет определенное и другое имя/описание/параметры каждый раз, когда он включается в другой (Например, если у меня есть цвет объекта, целые числа внутри него будут называться красным, синим, yello, а если объект является линейкой, его целое число будет называться length), поэтому у меня есть способ включить эту информацию в файл, а также их правильное соответствие соответствующим аргументам.

У вас есть какие-либо указания на то, что нужно искать/изучать/использовать/делать для такого проекта? Спасибо заранее.

+0

Какой общий формат вы имеете в виду? Будет ли использование XML работать для вас? –

ответ

0

Если у вас есть какие-то ограничения на формат ваших файлов, вы можете изучить XML или JSON для описания ваших грамматик.

Вы можете иметь файл грамматики, который выглядит как

{ 
    "ObjectTypes" : { 
     "ruler" : { "properties" : [ "length" ] }, 
     "color" : { "properties" : [ "red", "green", "blue" ] } 
    } 
} 

После чтения этого файла (с помощью предварительно существующей библиотеки, скорее всего), вы могли бы прочитать в другой файл, который будет иметь свои реальные объекты , Это может выглядеть примерно так:

{ 
    "Objects" : [ 
     { name : "object1", "type" : "ruler", "length" : 5 }, 
     { name : "object2", "type" : "color", "red" : 5, "blue" : 127, "green" : 150, } 
    ] 
} 

И так далее. Более подробный обзор JSON дается here, который включает ссылки на несколько библиотек C++, которые обрабатывают JSON (мой личный фаворит - JsonCpp).

+0

Я пытался использовать JSON и XML, но насколько я понял, они не поддерживают необязательные параметры или взаимозаменяемые параметры (это OR). Также вы не можете использовать определенный объект внутри другого.Например: 'Object1: \t Item1: \t \t Тип: \t \t \t Номер \t \t Описание: \t \t \t Первое описание \t \t Опция: \t \t \t Option1 \t \t \t Option2 \t Элемент2 : \t \t Тип: \t \t \t Object2 \t \t Описание: \t \t \t Второе описание \t Item3: \t \t Тип: \t \t \t Object3 \t \t Описание: \t \t \t Второе описание \t \t Объект1 Состав: \t Дополнительно (Item1) + (Item2 OR Item3) ' И так далее. Если я не смогу увидеть, как это сделать, я с удовольствием повторю попытку. – Svalorzen

+0

К сожалению, у меня недостаточно символов, чтобы изменить это лучше, но я надеюсь, что контент понятен. @Datalore – Svalorzen

+0

Я не понимаю, что вы подразумеваете под «Необязательными параметрами» или «Интершируемыми параметрами»; вы можете иметь произвольные пары ключ/значение внутри объектов JSON и произвольные списки внутри массивов JSON (взаимно вложенные по желанию). Вы можете прочитать из одного объекта JSON какую-то спецификацию, а затем использовать эту спецификацию, чтобы направить вашу программу на C++ при чтении другого набора объектов JSON и что-то сделать с ними. – Datalore

1

См. Earley parsers, которые анализируют контекстные бесплатные langauges, используя факты, извлеченные из грамматики, предоставленной во время выполнения.

Альтернативой является использование того факта, что практически все системы компилятора C++ предоставляют библиотеки, которые могут разветвлять процесс. Вы можете использовать это, чтобы развить сценарий оболочки, чтобы запустить любую схему генератора синтаксического анализа, которая вам нравится (в том числе Boost: Spirit, требующая, чтобы вы вызывали компилятор C++ из сценария, но это не сложно) на основе любого соответствующего грамматического формализма, а затем иметь этот скрипт вызывать сгенерированный парсер. Если у вас есть большие документы для обработки, это, вероятно, будет более эффективным, чем анализатор Эрли. Это, безусловно, будет намного проще реализовать.

+0

Ваше решение для вилки выглядит довольно неспортивным, к сожалению (я могу ошибаться, хотя). Я обязательно посмотрю на парнеры Earley, спасибо за ссылку! – Svalorzen

+0

Зависит от того, куда вы отправляетесь. Flex/Bison широко доступны, а вилка довольно стандартная примитивна. –

Смежные вопросы