add top level declarative structure

This commit is contained in:
Mark Thom
2017-05-09 16:26:17 -06:00
parent 9c72177b60
commit 6fa5bad5bf
6 changed files with 34 additions and 46 deletions

2
Cargo.lock generated
View File

@@ -1,6 +1,6 @@
[root]
name = "rusty-wam"
version = "0.6.2"
version = "0.6.3"
dependencies = [
"lalrpop 0.12.5 (registry+https://github.com/rust-lang/crates.io-index)",
"lalrpop-util 0.12.5 (registry+https://github.com/rust-lang/crates.io-index)",

View File

@@ -1,6 +1,6 @@
[package]
name = "rusty-wam"
version = "0.6.2"
version = "0.6.3"
authors = ["Mark Thom"]
build = "build.rs"

View File

@@ -46,11 +46,10 @@ prolog> ?- p(X, Y, Z).
Given the above work, the result of the query will be
```
prolog> ?- p(X, Y, Z).
yes
X = _0
true
Y = x
X = _0
Z = _2
Press ; to continue or . to abort.
```
Pressing ; will backtrack through other possible answers, if any exist.
@@ -63,40 +62,29 @@ prolog> :{
member(X, [X|_]).
member(X, [_|Xs]) :- member(X, Xs).
}:
prolog> ?- member(X, [a, b, c]).
yes
X = a
Press ; to continue or . to abort.
;
X = b
Press ; to continue or . to abort.
;
X = c
Press ; to continue or . to abort.
;
no
prolog> ?- member(X, [a, b, c]).
true
X = a ;
X = b ;
X = c ;
false.
```
and so do conjunctive queries:
```
prolog> ?- member([X,X],[a,b,c,[d,d],[e,d]]), member(X, [a,b,c,d,e,f,g]), member(Y, [X, a, b, c, d]).
yes
true
Y = d
X = d
Press ; to continue or . to abort.
X = d ;
Y = a
X = d
Press ; to continue or . to abort.
X = d ;
Y = b
X = d
Press ; to continue or . to abort.
X = d ;
Y = c
X = d
Press ; to continue or . to abort.
X = d ;
Y = d
X = d
Press ; to continue or . to abort.
no
X = d ;
false.
prolog>
```
@@ -114,6 +102,6 @@ term to a string results in an infinite loop, ie.
```
prolog> p(W, W).
prolog> ?- p(f(f(W)), W).
yes
true
*loops to infinity*
```

View File

@@ -24,7 +24,7 @@ pub enum VarStatus {
}
// Perm: 0 initially, a stack register once processed.
// Temp: labeled with chunk_num and temp offset (unassigned if 0), arg (0 if unassigned).
// Temp: labeled with chunk_num and temp offset (unassigned if 0).
pub enum VarData {
Perm(usize), Temp(usize, usize, TempVarData)
}

View File

@@ -304,49 +304,53 @@ Each predicate must have the same name and arity.";
pub fn print(wam: &mut Machine, result: EvalSession) {
match result {
EvalSession::InitialQuerySuccess(alloc_locs, mut heap_locs) => {
println!("yes");
println!("true");
if heap_locs.is_empty() {
return;
}
'outer: loop {
loop {
let mut result = EvalSession::QueryFailure;
let bindings = wam.heap_view(&heap_locs);
let stdin = stdin();
let mut stdout = stdout().into_raw_mode().unwrap();
write!(stdout, "{}\n\r", bindings).unwrap();
write!(stdout, "{}", bindings).unwrap();
stdout.flush().unwrap();
if !wam.or_stack_is_empty() {
write!(stdout, "Press ; to continue or . to abort.\n\r").unwrap();
stdout.flush().unwrap();
for c in stdin.keys() {
match c.unwrap() {
Key::Char(';') => {
write!(stdout, " ;\n\r").unwrap();
result = wam.continue_query(&alloc_locs, &mut heap_locs);
break;
},
Key::Char('.') =>
break 'outer,
Key::Char('.') => {
write!(stdout, " .\n\r").unwrap();
return;
},
_ => {}
}
}
if let &EvalSession::QueryFailure = &result {
write!(stdout, "no\n\r").unwrap();
write!(stdout, "false.\n\r").unwrap();
stdout.flush().unwrap();
break;
return;
}
} else {
} else {
break;
}
}
write!(stdout(), ".\n").unwrap();
},
EvalSession::QueryFailure => println!("no"),
EvalSession::QueryFailure => println!("false."),
_ => {}
};
}

View File

@@ -306,10 +306,6 @@ impl Machine {
-> EvalSession
{
if !self.or_stack_is_empty() {
if self.ms.b == 0 {
return EvalSession::QueryFailure;
}
let b = self.ms.b - 1;
self.ms.p = self.ms.or_stack[b].bp;
@@ -386,7 +382,7 @@ impl Machine {
}
pub fn or_stack_is_empty(&self) -> bool {
self.ms.or_stack.is_empty()
self.ms.b == 0
}
pub fn clear(&mut self) {