Objects, strings
This commit is contained in:
parent
51531b806f
commit
15055b9ece
@ -19,7 +19,7 @@ fn script(filename: &str) {
|
|||||||
let mut prgm = String::new();
|
let mut prgm = String::new();
|
||||||
file.read_to_string(&mut prgm).unwrap();
|
file.read_to_string(&mut prgm).unwrap();
|
||||||
let tree = parser::parse(&prgm);
|
let tree = parser::parse(&prgm);
|
||||||
println!("{:?}", tree);
|
println!("{:#?}", tree);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
|
@ -8,6 +8,7 @@ pub enum Stmt {
|
|||||||
#[derive(Debug,PartialEq,Clone)]
|
#[derive(Debug,PartialEq,Clone)]
|
||||||
pub enum Expr {
|
pub enum Expr {
|
||||||
Id(String),
|
Id(String),
|
||||||
|
String(String),
|
||||||
Num(f64),
|
Num(f64),
|
||||||
Funcall(String, Vec<Expr>),
|
Funcall(String, Vec<Expr>),
|
||||||
Funcdef(Option<String>, Box<Expr>),
|
Funcdef(Option<String>, Box<Expr>),
|
||||||
@ -17,6 +18,7 @@ pub enum Expr {
|
|||||||
Div(Box<Expr>, Box<Expr>),
|
Div(Box<Expr>, Box<Expr>),
|
||||||
Block(Vec<Stmt>),
|
Block(Vec<Stmt>),
|
||||||
GuardedBlock(Box<GuardedBlock>),
|
GuardedBlock(Box<GuardedBlock>),
|
||||||
|
Object(Vec<Stmt>),
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug,PartialEq,Clone)]
|
#[derive(Debug,PartialEq,Clone)]
|
||||||
@ -30,7 +32,7 @@ peg::parser! {
|
|||||||
pub rule program() -> Vec<Stmt>
|
pub rule program() -> Vec<Stmt>
|
||||||
= __* s:stmt()* { s }
|
= __* s:stmt()* { s }
|
||||||
pub rule stmt() -> Stmt
|
pub rule stmt() -> Stmt
|
||||||
= i:id() "<-" _ e:expr() stop() { Stmt::Assignment(i, e) } /
|
= a:assignment() { a } /
|
||||||
f:funcall() stop() { Stmt::Funcall(f) } /
|
f:funcall() stop() { Stmt::Funcall(f) } /
|
||||||
c:conditional() { c }
|
c:conditional() { c }
|
||||||
rule expr() -> Expr = precedence! {
|
rule expr() -> Expr = precedence! {
|
||||||
@ -41,14 +43,19 @@ peg::parser! {
|
|||||||
e1:(@) "/" _ e2:@ { Expr::Div(Box::new(e1), Box::new(e2)) }
|
e1:(@) "/" _ e2:@ { Expr::Div(Box::new(e1), Box::new(e2)) }
|
||||||
--
|
--
|
||||||
"(" _ e:expr() ")" _ { e }
|
"(" _ e:expr() ")" _ { e }
|
||||||
|
['"'] s:$((!['"'] [_] / r#"\""#)*) ['"'] { Expr::String(s.to_string()) }
|
||||||
f:funcall() { f }
|
f:funcall() { f }
|
||||||
f:funcdef() { f }
|
f:funcdef() { f }
|
||||||
|
o:object() { o }
|
||||||
i:id() _ { Expr::Id(i) }
|
i:id() _ { Expr::Id(i) }
|
||||||
n:num() _ { Expr::Num(n) }
|
n:num() _ { Expr::Num(n) }
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
rule id() -> String
|
rule id() -> String
|
||||||
= i:$(letter() (letter() / digit() / ['?'|'.'|'-'])*) _ { i.to_string() }
|
= i:$(letter() (letter() / digit() / ['?'|'.'|'-'])*) _ { i.to_string() }
|
||||||
|
rule assignment() -> Stmt
|
||||||
|
= i:id() "<-" _ e:expr() stop() { Stmt::Assignment(i, e) }
|
||||||
rule num() -> f64
|
rule num() -> f64
|
||||||
= n:$(digit()+ "."? digit()* / "." digit()+) _ { n.parse().unwrap() }
|
= n:$(digit()+ "."? digit()* / "." digit()+) _ { n.parse().unwrap() }
|
||||||
rule funcall() -> Expr
|
rule funcall() -> Expr
|
||||||
@ -57,6 +64,9 @@ peg::parser! {
|
|||||||
= i:id()? "->" _ e:(expr() / block()) { Expr::Funcdef(i, Box::new(e)) }
|
= i:id()? "->" _ e:(expr() / block()) { Expr::Funcdef(i, Box::new(e)) }
|
||||||
rule conditional() -> Stmt
|
rule conditional() -> Stmt
|
||||||
= i:_if() __* ei:elif()* __* e:_else()? __* { Stmt::Conditional([vec![i], ei].concat(), e) }
|
= i:_if() __* ei:elif()* __* e:_else()? __* { Stmt::Conditional([vec![i], ei].concat(), e) }
|
||||||
|
rule object() -> Expr
|
||||||
|
= "{" _ stop() indent() __* a:assignment()+ dedent() __* "}" _ { Expr::Object(a) }
|
||||||
|
|
||||||
rule _if() -> Expr
|
rule _if() -> Expr
|
||||||
= "if" _ g:expr() b:indented_block() {
|
= "if" _ g:expr() b:indented_block() {
|
||||||
Expr::GuardedBlock(Box::new(GuardedBlock {
|
Expr::GuardedBlock(Box::new(GuardedBlock {
|
||||||
@ -305,6 +315,22 @@ else
|
|||||||
)];
|
)];
|
||||||
assert_eq!(deelang_parser::program(prgm).unwrap(), expected);
|
assert_eq!(deelang_parser::program(prgm).unwrap(), expected);
|
||||||
}
|
}
|
||||||
|
#[test]
|
||||||
|
fn test_object() {
|
||||||
|
let prgm = r"fruit <- {
|
||||||
|
>>>apple <- 1
|
||||||
|
pear <- 2
|
||||||
|
<<<
|
||||||
|
}";
|
||||||
|
let expected = vec![Stmt::Assignment(
|
||||||
|
"fruit".to_string(),
|
||||||
|
Expr::Object(vec![
|
||||||
|
Stmt::Assignment("apple".to_string(), Expr::Num(1.0)),
|
||||||
|
Stmt::Assignment("pear".to_string(), Expr::Num(2.0)),
|
||||||
|
]),
|
||||||
|
)];
|
||||||
|
assert_eq!(deelang_parser::program(prgm).unwrap(), expected);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_preprocess() {
|
fn test_preprocess() {
|
||||||
|
Loading…
Reference in New Issue
Block a user