mirror of
https://github.com/GayPizzaSpecifications/pork.git
synced 2025-08-02 21:00:56 +00:00
language: today, we killed lambdas
This commit is contained in:
parent
073ea09b13
commit
ddff6cb365
@ -115,13 +115,6 @@ types:
|
|||||||
values:
|
values:
|
||||||
- name: value
|
- name: value
|
||||||
type: Int
|
type: Int
|
||||||
Lambda:
|
|
||||||
parent: Expression
|
|
||||||
values:
|
|
||||||
- name: arguments
|
|
||||||
type: List<Symbol>
|
|
||||||
- name: expressions
|
|
||||||
type: List<Expression>
|
|
||||||
ListLiteral:
|
ListLiteral:
|
||||||
parent: Expression
|
parent: Expression
|
||||||
values:
|
values:
|
||||||
|
@ -1,29 +0,0 @@
|
|||||||
// GENERATED CODE FROM PORK AST CODEGEN
|
|
||||||
package gay.pizza.pork.ast
|
|
||||||
|
|
||||||
import kotlinx.serialization.SerialName
|
|
||||||
import kotlinx.serialization.Serializable
|
|
||||||
|
|
||||||
@Serializable
|
|
||||||
@SerialName("lambda")
|
|
||||||
class Lambda(val arguments: List<Symbol>, val expressions: List<Expression>) : Expression() {
|
|
||||||
override val type: NodeType = NodeType.Lambda
|
|
||||||
|
|
||||||
override fun <T> visitChildren(visitor: NodeVisitor<T>): List<T> =
|
|
||||||
visitor.visitAll(arguments, expressions)
|
|
||||||
|
|
||||||
override fun <T> visit(visitor: NodeVisitor<T>): T =
|
|
||||||
visitor.visitLambda(this)
|
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
|
||||||
if (other !is Lambda) return false
|
|
||||||
return other.arguments == arguments && other.expressions == expressions
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun hashCode(): Int {
|
|
||||||
var result = arguments.hashCode()
|
|
||||||
result = 31 * result + expressions.hashCode()
|
|
||||||
result = 31 * result + type.hashCode()
|
|
||||||
return result
|
|
||||||
}
|
|
||||||
}
|
|
@ -29,9 +29,6 @@ class NodeCoalescer(val handler: (Node) -> Unit) : NodeVisitor<Unit> {
|
|||||||
override fun visitIntLiteral(node: IntLiteral): Unit =
|
override fun visitIntLiteral(node: IntLiteral): Unit =
|
||||||
handle(node)
|
handle(node)
|
||||||
|
|
||||||
override fun visitLambda(node: Lambda): Unit =
|
|
||||||
handle(node)
|
|
||||||
|
|
||||||
override fun visitLetAssignment(node: LetAssignment): Unit =
|
override fun visitLetAssignment(node: LetAssignment): Unit =
|
||||||
handle(node)
|
handle(node)
|
||||||
|
|
||||||
|
@ -15,7 +15,6 @@ enum class NodeType(val parent: NodeType? = null) {
|
|||||||
ImportDeclaration(Declaration),
|
ImportDeclaration(Declaration),
|
||||||
InfixOperation(Expression),
|
InfixOperation(Expression),
|
||||||
IntLiteral(Expression),
|
IntLiteral(Expression),
|
||||||
Lambda(Expression),
|
|
||||||
LetAssignment(Expression),
|
LetAssignment(Expression),
|
||||||
ListLiteral(Expression),
|
ListLiteral(Expression),
|
||||||
Parentheses(Expression),
|
Parentheses(Expression),
|
||||||
|
@ -20,8 +20,6 @@ interface NodeVisitor<T> {
|
|||||||
|
|
||||||
fun visitIntLiteral(node: IntLiteral): T
|
fun visitIntLiteral(node: IntLiteral): T
|
||||||
|
|
||||||
fun visitLambda(node: Lambda): T
|
|
||||||
|
|
||||||
fun visitLetAssignment(node: LetAssignment): T
|
fun visitLetAssignment(node: LetAssignment): T
|
||||||
|
|
||||||
fun visitListLiteral(node: ListLiteral): T
|
fun visitListLiteral(node: ListLiteral): T
|
||||||
|
@ -14,7 +14,6 @@ fun <T> NodeVisitor<T>.visit(node: Node): T =
|
|||||||
is If -> visitIf(node)
|
is If -> visitIf(node)
|
||||||
is ImportDeclaration -> visitImportDeclaration(node)
|
is ImportDeclaration -> visitImportDeclaration(node)
|
||||||
is IntLiteral -> visitIntLiteral(node)
|
is IntLiteral -> visitIntLiteral(node)
|
||||||
is Lambda -> visitLambda(node)
|
|
||||||
is ListLiteral -> visitListLiteral(node)
|
is ListLiteral -> visitListLiteral(node)
|
||||||
is Parentheses -> visitParentheses(node)
|
is Parentheses -> visitParentheses(node)
|
||||||
is PrefixOperation -> visitPrefixOperation(node)
|
is PrefixOperation -> visitPrefixOperation(node)
|
||||||
|
@ -27,24 +27,6 @@ class EvaluationVisitor(root: Scope) : NodeVisitor<Any> {
|
|||||||
override fun visitSymbolReference(node: SymbolReference): Any =
|
override fun visitSymbolReference(node: SymbolReference): Any =
|
||||||
currentScope.value(node.symbol.id)
|
currentScope.value(node.symbol.id)
|
||||||
|
|
||||||
override fun visitLambda(node: Lambda): CallableFunction {
|
|
||||||
return CallableFunction { arguments ->
|
|
||||||
currentScope = currentScope.fork()
|
|
||||||
for ((index, argumentSymbol) in node.arguments.withIndex()) {
|
|
||||||
currentScope.define(argumentSymbol.id, arguments.values[index])
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
var value: Any? = null
|
|
||||||
for (expression in node.expressions) {
|
|
||||||
value = expression.visit(this)
|
|
||||||
}
|
|
||||||
value ?: None
|
|
||||||
} finally {
|
|
||||||
currentScope = currentScope.leave()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun visitParentheses(node: Parentheses): Any =
|
override fun visitParentheses(node: Parentheses): Any =
|
||||||
node.expression.visit(this)
|
node.expression.visit(this)
|
||||||
|
|
||||||
|
@ -1,55 +0,0 @@
|
|||||||
export func main() {
|
|
||||||
let three = 3
|
|
||||||
let two = 2
|
|
||||||
|
|
||||||
let calculateSimple = { in
|
|
||||||
(50 + three) * two
|
|
||||||
}
|
|
||||||
|
|
||||||
let calculateComplex = { in
|
|
||||||
three + two + 50
|
|
||||||
}
|
|
||||||
|
|
||||||
let multiply = { a, b in
|
|
||||||
a * b
|
|
||||||
}
|
|
||||||
|
|
||||||
// calculates the result
|
|
||||||
let calculateSimpleResult = calculateSimple()
|
|
||||||
let calculateComplexResult = calculateComplex()
|
|
||||||
let multiplyResult = multiply(50, 50)
|
|
||||||
|
|
||||||
let list = [10, 20, 30]
|
|
||||||
let trueValue = true
|
|
||||||
let falseValue = false
|
|
||||||
|
|
||||||
let invert = { value in
|
|
||||||
!value
|
|
||||||
}
|
|
||||||
|
|
||||||
let notEqual = { a, b in
|
|
||||||
a != b
|
|
||||||
}
|
|
||||||
|
|
||||||
let equal = { a, b in
|
|
||||||
a == b
|
|
||||||
}
|
|
||||||
|
|
||||||
let results = [
|
|
||||||
calculateSimpleResult,
|
|
||||||
calculateComplexResult,
|
|
||||||
multiplyResult,
|
|
||||||
list,
|
|
||||||
trueValue,
|
|
||||||
falseValue,
|
|
||||||
invert(true),
|
|
||||||
invert(false),
|
|
||||||
equal(5, 5),
|
|
||||||
equal(5, 6),
|
|
||||||
notEqual(5, 5),
|
|
||||||
notEqual(5, 6)
|
|
||||||
]
|
|
||||||
|
|
||||||
println("results:")
|
|
||||||
println(results)
|
|
||||||
}
|
|
@ -8,11 +8,14 @@ import gay.pizza.pork.parser.TokenStreamSource
|
|||||||
import gay.pizza.pork.parser.Tokenizer
|
import gay.pizza.pork.parser.Tokenizer
|
||||||
|
|
||||||
class World(val contentSource: ContentSource) {
|
class World(val contentSource: ContentSource) {
|
||||||
private val units = mutableMapOf<String, CompilationUnit>()
|
private val internalUnits = mutableMapOf<String, CompilationUnit>()
|
||||||
|
|
||||||
|
val units: List<CompilationUnit>
|
||||||
|
get() = internalUnits.values.toList()
|
||||||
|
|
||||||
private fun loadOneUnit(path: String): CompilationUnit {
|
private fun loadOneUnit(path: String): CompilationUnit {
|
||||||
val stableIdentity = contentSource.stableContentIdentity(path)
|
val stableIdentity = contentSource.stableContentIdentity(path)
|
||||||
val cached = units[stableIdentity]
|
val cached = internalUnits[stableIdentity]
|
||||||
if (cached != null) {
|
if (cached != null) {
|
||||||
return cached
|
return cached
|
||||||
}
|
}
|
||||||
|
@ -56,26 +56,6 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun readLambda(): Lambda = within {
|
|
||||||
expect(TokenType.LeftCurly)
|
|
||||||
val arguments = mutableListOf<Symbol>()
|
|
||||||
while (!peek(TokenType.In)) {
|
|
||||||
val symbol = readSymbolRaw()
|
|
||||||
arguments.add(symbol)
|
|
||||||
if (next(TokenType.Comma)) {
|
|
||||||
continue
|
|
||||||
} else {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
expect(TokenType.In)
|
|
||||||
val items = collect(TokenType.RightCurly) {
|
|
||||||
readExpression()
|
|
||||||
}
|
|
||||||
expect(TokenType.RightCurly)
|
|
||||||
Lambda(arguments, items)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun readParentheses(): Parentheses = within {
|
private fun readParentheses(): Parentheses = within {
|
||||||
expect(TokenType.LeftParentheses)
|
expect(TokenType.LeftParentheses)
|
||||||
val expression = readExpression()
|
val expression = readExpression()
|
||||||
@ -128,10 +108,6 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
|
|||||||
readSymbolCases()
|
readSymbolCases()
|
||||||
}
|
}
|
||||||
|
|
||||||
TokenType.LeftCurly -> {
|
|
||||||
readLambda()
|
|
||||||
}
|
|
||||||
|
|
||||||
TokenType.LeftParentheses -> {
|
TokenType.LeftParentheses -> {
|
||||||
readParentheses()
|
readParentheses()
|
||||||
}
|
}
|
||||||
|
@ -82,34 +82,6 @@ class Printer(buffer: StringBuilder) : NodeVisitor<Unit> {
|
|||||||
visit(node.symbol)
|
visit(node.symbol)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun visitLambda(node: Lambda) {
|
|
||||||
append("{")
|
|
||||||
if (node.arguments.isNotEmpty()) {
|
|
||||||
append(" ")
|
|
||||||
for ((index, argument) in node.arguments.withIndex()) {
|
|
||||||
visit(argument)
|
|
||||||
if (index + 1 != node.arguments.size) {
|
|
||||||
append(",")
|
|
||||||
}
|
|
||||||
append(" ")
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
append(" ")
|
|
||||||
}
|
|
||||||
append("in")
|
|
||||||
out.increaseIndent()
|
|
||||||
for (expression in node.expressions) {
|
|
||||||
appendLine()
|
|
||||||
visit(expression)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (node.expressions.isNotEmpty()) {
|
|
||||||
appendLine()
|
|
||||||
}
|
|
||||||
out.decreaseIndent()
|
|
||||||
append("}")
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun visitParentheses(node: Parentheses) {
|
override fun visitParentheses(node: Parentheses) {
|
||||||
append("(")
|
append("(")
|
||||||
visit(node.expression)
|
visit(node.expression)
|
||||||
|
@ -24,7 +24,6 @@ enum class TokenType(vararg properties: TokenTypeProperty) {
|
|||||||
Comma(SingleChar(',')),
|
Comma(SingleChar(',')),
|
||||||
False(Keyword("false"), KeywordFamily),
|
False(Keyword("false"), KeywordFamily),
|
||||||
True(Keyword("true"), KeywordFamily),
|
True(Keyword("true"), KeywordFamily),
|
||||||
In(Keyword("in"), KeywordFamily),
|
|
||||||
If(Keyword("if"), KeywordFamily),
|
If(Keyword("if"), KeywordFamily),
|
||||||
Then(Keyword("then"), KeywordFamily),
|
Then(Keyword("then"), KeywordFamily),
|
||||||
Else(Keyword("else"), KeywordFamily),
|
Else(Keyword("else"), KeywordFamily),
|
||||||
|
Loading…
Reference in New Issue
Block a user