Skip to content

Instantly share code, notes, and snippets.

@Victorious3
Created July 27, 2018 08:31
Show Gist options
  • Save Victorious3/13628fe71cefd6321952bf9c53bab2cd to your computer and use it in GitHub Desktop.
Save Victorious3/13628fe71cefd6321952bf9c53bab2cd to your computer and use it in GitHub Desktop.
import norswap.autumn.Grammar
import norswap.autumn.Parser
import norswap.autumn.parsers.*
interface Expression
data class Number(val value: Int): Expression
data class Add(val left: Expression, val right: Expression): Expression
data class Sub(val left: Expression, val right: Expression): Expression
/*
Equivalent TatSu Grammar
@@left_recursion :: True
start = expression $;
number = /\d+/;
addition = expression '+' number;
subtraction = expression '-' number;
expression =
| addition
| subtraction
| number;
*/
class CalcGrammar: Grammar() {
fun number() = build_str (
syntax = { repeat1 { char_range('0', '9') } },
value = { Number(it.toInt()) }
)
fun addition(expr: Parser) = build (
syntax = { seq { expr() && string("+") && number() } },
effect = { Add(it(0), it(1)) }
)
fun subtraction(expr: Parser) = build (
syntax = { seq { expr() && string("-") && number() } },
effect = { Sub(it(0), it(1)) }
)
val expression = leftrec { self ->
choice {
addition(self) || subtraction(self) || number()
}
}
override fun root() = expression()
}
fun diagnose (grammar: Grammar, input: String) {
if (grammar.parse(input)) println("success: " + grammar.stack)
else println("failure: " + grammar.failure?.invoke())
grammar.reset()
}
fun main (args: Array<String>) {
val grammar = CalcGrammar()
diagnose(grammar, "1+1-1")
diagnose(grammar, "1-1+1")
}
@Victorious3
Copy link
Author

Output:

success: [Sub(left=Add(left=Number(value=1), right=Number(value=1)), right=Number(value=1))]
success: [Add(left=Sub(left=Number(value=1), right=Number(value=1)), right=Number(value=1))]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment