transition to l3
This commit is contained in:
264
src/main.rs
264
src/main.rs
@@ -1,157 +1,203 @@
|
||||
mod l2;
|
||||
extern crate termion;
|
||||
mod l3;
|
||||
|
||||
use l2::ast::*;
|
||||
use l2::codegen::*;
|
||||
use l2::machine::*;
|
||||
|
||||
use std::io::{self, Write};
|
||||
|
||||
fn submit(wam: &mut Machine, buffer: String) -> bool {
|
||||
let result = l2::l2_parser::parse_TopLevel(&*buffer);
|
||||
|
||||
let mut cg = CodeGenerator::new();
|
||||
|
||||
match &result {
|
||||
&Ok(TopLevel::Fact(ref fact)) => {
|
||||
let compiled_fact = cg.compile_fact(&fact);
|
||||
wam.add_fact(fact, compiled_fact);
|
||||
},
|
||||
&Ok(TopLevel::Rule(ref rule)) => {
|
||||
let compiled_rule = cg.compile_rule(&rule);
|
||||
wam.add_rule(rule, compiled_rule);
|
||||
},
|
||||
&Ok(TopLevel::Query(ref query)) => {
|
||||
let compiled_query = cg.compile_query(&query);
|
||||
let output = wam.run_query(compiled_query, &cg);
|
||||
|
||||
match output {
|
||||
Some(result) => {
|
||||
println!("yes");
|
||||
|
||||
if result != "" {
|
||||
println!("{}", result);
|
||||
}
|
||||
},
|
||||
None => println!("no")
|
||||
}
|
||||
},
|
||||
&Err(_) => println!("Grammatical error of some kind!"),
|
||||
};
|
||||
|
||||
let result = wam.failed();
|
||||
wam.reset();
|
||||
result
|
||||
}
|
||||
use l3::io::*;
|
||||
use l3::machine::*;
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[inline]
|
||||
fn submit_ss(wam: &mut Machine, buffer: &'static str) -> bool {
|
||||
submit(wam, String::from(buffer))
|
||||
use l3::ast::*;
|
||||
|
||||
fn submit(wam: &mut Machine, buffer: &str) -> EvalResult {
|
||||
let result = eval(wam, buffer);
|
||||
wam.reset();
|
||||
result
|
||||
}
|
||||
|
||||
|
||||
#[test]
|
||||
fn test_queries_on_facts() {
|
||||
let mut wam = Machine::new();
|
||||
|
||||
submit_ss(&mut wam, "p(Z, Z).");
|
||||
submit_ss(&mut wam, "clouds(are, nice).");
|
||||
submit(&mut wam, "p(Z, Z).");
|
||||
submit(&mut wam, "clouds(are, nice).");
|
||||
|
||||
// submit_ss returns true on failure, false on success.
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, Z)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, z)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, w)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(z, w)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(w, w)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- clouds(Z, Z)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- clouds(are, Z)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- clouds(Z, nice)."), false);
|
||||
// submit returns true on failure, false on success.
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, w).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(z, w).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(w, w).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- clouds(Z, Z).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- clouds(are, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- clouds(Z, nice).").failed_query(), false);
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, h(Z, W), f(W))."), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, h(Z, W), f(W)).").failed_query(), true);
|
||||
|
||||
submit_ss(&mut wam, "p(Z, h(Z, W), f(W)).");
|
||||
submit(&mut wam, "p(Z, h(Z, W), f(W)).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(z, h(z, z), f(w))."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(z, h(z, w), f(w))."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(z, h(z, W), f(w))."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, h(Z, w), f(Z))."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(z, h(Z, w), f(Z))."), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(z, h(z, z), f(w)).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(z, h(z, w), f(w)).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(z, h(z, W), f(w)).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, h(Z, w), f(Z)).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(z, h(Z, w), f(Z)).").failed_query(), true);
|
||||
|
||||
submit_ss(&mut wam, "p(f(X), h(Y, f(a)), Y).");
|
||||
submit(&mut wam, "p(f(X), h(Y, f(a)), Y).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, h(Z, W), f(W))."), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, h(Z, W), f(W)).").failed_query(), false);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_queries_on_rules() {
|
||||
let mut wam = Machine::new();
|
||||
|
||||
submit_ss(&mut wam, "p(X, Y) :- q(X, Z), r(Z, Y).");
|
||||
submit_ss(&mut wam, "q(q, s).");
|
||||
submit_ss(&mut wam, "r(s, t).");
|
||||
submit(&mut wam, "p(X, Y) :- q(X, Z), r(Z, Y).");
|
||||
submit(&mut wam, "q(q, s).");
|
||||
submit(&mut wam, "r(s, t).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(X, Y)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(q, t)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(t, q)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(q, T)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Q, t)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(t, t)."), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(q, t).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(t, q).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(q, T).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Q, t).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(t, t).").failed_query(), true);
|
||||
|
||||
submit_ss(&mut wam, "p(X, Y) :- q(f(f(X)), R), r(S, T).");
|
||||
submit_ss(&mut wam, "q(f(f(X)), r).");
|
||||
submit(&mut wam, "p(X, Y) :- q(f(f(X)), R), r(S, T).");
|
||||
submit(&mut wam, "q(f(f(X)), r).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(X, Y)."), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
|
||||
submit_ss(&mut wam, "q(f(f(x)), r).");
|
||||
submit(&mut wam, "q(f(f(x)), r).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(X, Y)."), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
|
||||
submit_ss(&mut wam, "p(X, Y) :- q(X, Y), r(X, Y).");
|
||||
submit_ss(&mut wam, "q(s, t).");
|
||||
submit_ss(&mut wam, "r(X, Y) :- r(a).");
|
||||
submit_ss(&mut wam, "r(a).");
|
||||
submit(&mut wam, "p(X, Y) :- q(X, Y), r(X, Y).");
|
||||
submit(&mut wam, "q(s, t).");
|
||||
submit(&mut wam, "r(X, Y) :- r(a).");
|
||||
submit(&mut wam, "r(a).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(X, Y)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(t, S)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(t, s)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(s, T)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(S, t)."), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(t, S).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(t, s).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(s, T).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(S, t).").failed_query(), false);
|
||||
|
||||
submit_ss(&mut wam, "p(f(f(a), g(b), X), g(b), h) :- q(X, Y).");
|
||||
submit_ss(&mut wam, "q(X, Y).");
|
||||
submit(&mut wam, "p(f(f(a), g(b), X), g(b), h) :- q(X, Y).");
|
||||
submit(&mut wam, "q(X, Y).");
|
||||
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(f(X, Y, Z), g(b), h)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(f(X, g(Y), Z), g(Z), X)."), true);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(f(X, g(Y), Z), g(Z), h)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(Z, Y, X)."), false);
|
||||
assert_eq!(submit_ss(&mut wam, "?- p(f(X, Y, Z), Y, h)."), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(X, Y, Z), g(b), h).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(X, g(Y), Z), g(Z), X).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(X, g(Y), Z), g(Z), h).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(Z, Y, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(X, Y, Z), Y, h).").failed_query(), false);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_queries_on_predicates() {
|
||||
let mut wam = Machine::new();
|
||||
|
||||
submit(&mut wam, "p(X, a). p(b, X).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(x, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(b, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(b, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, b).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "p(X, Y, a). p(X, a, Y). p(X, Y, a).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(c, d, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, a, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(b, c, d).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "p(X, a). p(X, Y) :- q(Z), p(X, X).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(x, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, b).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "q(z).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, b).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(x, a).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
|
||||
submit(&mut wam, "p(X, a). p(X, Y) :- q(Y), p(X, X).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, b).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "p(a, z). p(X, Y) :- q(Y), p(X, Y).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(b, a).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "p(X, Y, Z) :- q(X), r(Y), s(Z).
|
||||
p(a, b, Z) :- q(Z).");
|
||||
|
||||
submit(&mut wam, "q(x).");
|
||||
submit(&mut wam, "r(y).");
|
||||
submit(&mut wam, "s(z).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, b, c).").failed_query(), true);
|
||||
assert_eq!(submit(&mut wam, "?- p(a, b, C).").failed_query(), false);
|
||||
|
||||
submit(&mut wam, "p(X) :- q(X). p(X) :- r(X).");
|
||||
submit(&mut wam, "q(X) :- a.");
|
||||
submit(&mut wam, "r(X) :- s(X, t). r(X) :- t(X, u).");
|
||||
|
||||
submit(&mut wam, "s(x, t).");
|
||||
submit(&mut wam, "t(y, u).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(x).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(y).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(z).").failed_query(), true);
|
||||
|
||||
submit(&mut wam, "p(f(f(X)), h(W), Y) :- g(W), h(W), f(X).
|
||||
p(X, Y, Z) :- h(Y), g(W), z(Z).");
|
||||
submit(&mut wam, "g(f(X)) :- z(X). g(X) :- h(X).");
|
||||
submit(&mut wam, "h(w). h(x). h(z).");
|
||||
submit(&mut wam, "f(s).");
|
||||
submit(&mut wam, "z(Z).");
|
||||
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, X, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(f(Z)), Y, Z).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, X, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(X, Y, X).").failed_query(), false);
|
||||
assert_eq!(submit(&mut wam, "?- p(f(f(X)), h(f(X)), Y).").failed_query(), true);
|
||||
}
|
||||
}
|
||||
|
||||
fn l2_repl() {
|
||||
fn l3_repl() {
|
||||
let mut wam = Machine::new();
|
||||
|
||||
|
||||
loop {
|
||||
print!("l2> ");
|
||||
print!("l3> ");
|
||||
|
||||
let _ = io::stdout().flush();
|
||||
let mut buffer = String::new();
|
||||
let buffer = read();
|
||||
|
||||
io::stdin().read_line(&mut buffer).unwrap();
|
||||
|
||||
if &*buffer == "quit\n" {
|
||||
if buffer == "quit\n" {
|
||||
break;
|
||||
} else if &*buffer == "clear\n" {
|
||||
} else if buffer == "clear\n" {
|
||||
wam = Machine::new();
|
||||
continue;
|
||||
}
|
||||
|
||||
submit(&mut wam, buffer);
|
||||
let result = eval(&mut wam, buffer.trim());
|
||||
print(&mut wam, result);
|
||||
|
||||
wam.reset();
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
l2_repl();
|
||||
l3_repl();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user