98 lines
2.5 KiB
Kotlin
98 lines
2.5 KiB
Kotlin
import better_parser.PrologParser
|
|
import better_parser.SimpleReplParser
|
|
import interpreter.SourceFileReader
|
|
import prolog.Answer
|
|
import prolog.Program
|
|
import prolog.ast.logic.Fact
|
|
import prolog.ast.logic.Rule
|
|
import prolog.ast.terms.Atom
|
|
import prolog.ast.terms.CompoundTerm
|
|
import prolog.ast.terms.Variable
|
|
import prolog.builtins.Conjunction
|
|
|
|
fun help(): String {
|
|
println("Unknown command. Type 'h' for help.")
|
|
println("Commands:")
|
|
println(" ; - find next solution")
|
|
println(" a - abort")
|
|
println(" . - end query")
|
|
println(" h - help")
|
|
println(" exit - exit Prolog REPL")
|
|
return ""
|
|
}
|
|
|
|
fun say(message: String) {
|
|
println(message)
|
|
}
|
|
|
|
fun prompt(message: String): String {
|
|
print("$message ")
|
|
var input: String = readlnOrNull() ?: help()
|
|
while (input.isBlank()) {
|
|
input = readlnOrNull() ?: help()
|
|
}
|
|
return input
|
|
}
|
|
|
|
fun prettyResult(result: Answer): String {
|
|
result.fold(
|
|
onSuccess = {
|
|
val subs = result.getOrNull()!!
|
|
if (subs.isEmpty()) {
|
|
return "true."
|
|
}
|
|
return subs.entries.joinToString(", ") { "${it.key} = ${it.value}" }
|
|
},
|
|
onFailure = {
|
|
return "Failure: ${result.exceptionOrNull()!!}"
|
|
}
|
|
)
|
|
}
|
|
|
|
val knownCommands = setOf(";", "a", ".")
|
|
|
|
fun main() {
|
|
SourceFileReader().readFile("tests/better_parser/resources/parent.pl")
|
|
|
|
val parser = SimpleReplParser(debug = false)
|
|
|
|
say("Prolog REPL. Type 'exit' to quit.")
|
|
|
|
while (true) {
|
|
val queryString = prompt("?-")
|
|
|
|
try {
|
|
val query = parser.parse(queryString)
|
|
val answers = query.satisfy(emptyMap())
|
|
|
|
if (answers.none()) {
|
|
say("false.")
|
|
} else {
|
|
val iterator = answers.iterator()
|
|
|
|
var previous = iterator.next()
|
|
|
|
while (iterator.hasNext()) {
|
|
var command = prompt(prettyResult(previous))
|
|
|
|
while (command !in knownCommands) {
|
|
say("Unknown action: $command (h for help)")
|
|
command = prompt("Action?")
|
|
}
|
|
|
|
when (command) {
|
|
";" -> previous = iterator.next()
|
|
"a" -> break
|
|
"." -> break
|
|
}
|
|
}
|
|
|
|
say(prettyResult(previous))
|
|
}
|
|
|
|
} catch (e: Exception) {
|
|
println("Error: ${e.message}")
|
|
}
|
|
}
|
|
|
|
}
|