/GrammarParser

Contains simple grammar generator

Primary LanguageC#MIT LicenseMIT

Travis CI

GrammarParser

Структура лексера

Файл, содержащий специйикаацию для парсера имеют определенную структуру. Структурные элементы (Блоки) определяются следующим образом:

block BLOCK_NAME {
...
}

Внутри блока описывается что-то по правилам этого самого блокаю.

Rules

Содержит правила для лексера.

block Rules {
   ruleName: rule -> Name: rule;
   ...
}

ruleName - имя правила. Может состоять из букв и цифр. rule - само правило, записанное на формальном языке. -> - спец символ, указывающий в какой вид узла преобразовать символы, если правило выполнилось. Далее следует спрециальный синтаксис для описания формата узла.

Пример:

block Rules {
   words: 'a'..'z'+' '+'a'..'z'+ -> Name: "Node name", FirstWord: 1, SecondWord: 3;
   ...
}

Если это правило отработает, то дерево, полученное из этого правило будет иметь следующий вид:

Если этому правилу передать строку: abc def

{
   "name": "Node name",
   "value": null,
   "childs": [
      {
         "name": "FirstWord",
         "value": "abc",
         "childs": null
      },
      {
         "name": "SecondWord",
         "value": "def",
         "childs": null
      }
   ]
}

Aliases

Набор токенов, которыми можно заменить сложные правила в лексере. Блок имеет следующдий синтаксис:

block Aliases {
   key1: value
   key2: value
   ...
}

В дальшнейшем key можно использовтаь в лексере.

Пример:

block Aliases {
   CharacterAlias = ('a'..'z')|('A'..'Z')
   StringAlias = AnyCharacter+
   AnyDigitAlias = ('0'..'9')
   AnyIntegerAlias = AnyDigit+
   ...
}

...

StringAlias|AnyIntegerAlias

Правила лексера:

Обозначения:

r - любое правило. s - любой символ

  • () - группировка
  • 's' - обычный символ.
  • r? - Символ либо не встречается, либо встречается, но только 1 раз.
  • r* - Символ либо не встречается, либо может встреится ниограниченное число раз.
  • r+ - Символ должен встретится как минимум 1 раз.
  • 's1'..'s2' - Множество символов начиная с s1, заканчивая s2 (включая крайнией символы)
  • r|r - Правило ИЛИ. Если выполняется первое правило, то второе проверяться не будет.

Примеры

  • 's':

    'a' <- b = false
    'a' <- a = true

  • r?:

    'a'? <- b = true
    'a'? <- a = true
    'a'? <- = true

  • r*:

    'a'* <- b = true
    'a'* <- a = true
    'a'* <- aaaaaaaaaaaaaa = true
    'a'* <- = true

  • r+:

    'a'+ <- b = false
    'a'+ <- a = true
    'a'+ <- aaaaaaaaaaaaaa = true
    'a'+ <- = false

  • 's1'..'s2':

    'a'..'c' <- d = false
    'a'..'c' <- b = true
    'a'..'c' <- a = true
    'a'..'c' <- c = true

  • r|r:

    'a'|'b' <- c = false
    'a'|'b' <- b = true
    'a'|'b' <- a = true