(Largely) trait-ify Schala
The idea is to provide a trait `ProgrammingLanguage` that actually does all the work, and then main.rs will just be the infra for storing its own state
This commit is contained in:
parent
5e474231da
commit
8326a12c9c
@ -8,12 +8,12 @@ pub struct ParseError {
|
|||||||
pub msg: String,
|
pub msg: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub trait ProgrammingLanguage {
|
pub trait ProgrammingLanguage<Evaluator> {
|
||||||
type Token: Debug;
|
type Token: Debug;
|
||||||
type AST: Debug;
|
type AST: Debug;
|
||||||
|
|
||||||
fn tokenize(input: &str) -> Result<Vec<Self::Token>, TokenError>;
|
fn tokenize(input: &str) -> Result<Vec<Self::Token>, TokenError>;
|
||||||
fn parse(input: Vec<Self::Token>) -> Result<Self::AST, ParseError>;
|
fn parse(input: Vec<Self::Token>) -> Result<Self::AST, ParseError>;
|
||||||
fn evaluate(input: &Self::AST);
|
fn evaluate(input: Self::AST, evaluator: &mut Evaluator) -> Vec<String>;
|
||||||
fn compile(input: &Self::AST);
|
fn compile(input: &Self::AST);
|
||||||
}
|
}
|
||||||
|
20
src/main.rs
20
src/main.rs
@ -148,9 +148,14 @@ impl<'a> Repl<'a> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn input_handler(&mut self, input: &str) -> String {
|
fn input_handler(&mut self, input: &str) -> String {
|
||||||
|
let schala = Schala { };
|
||||||
|
self.input_handler_new(input, schala)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn input_handler_new<T: ProgrammingLanguage<eval::Evaluator<'a>>>(&mut self, input: &str, language: T) -> String {
|
||||||
let mut output = String::new();
|
let mut output = String::new();
|
||||||
|
|
||||||
let tokens = match tokenize(input) {
|
let tokens = match T::tokenize(input) {
|
||||||
Ok(tokens) => tokens,
|
Ok(tokens) => tokens,
|
||||||
Err(err) => {
|
Err(err) => {
|
||||||
output.push_str(&format!("Tokenization error: {}\n", err.msg));
|
output.push_str(&format!("Tokenization error: {}\n", err.msg));
|
||||||
@ -162,7 +167,7 @@ impl<'a> Repl<'a> {
|
|||||||
output.push_str(&format!("Tokens: {:?}\n", tokens));
|
output.push_str(&format!("Tokens: {:?}\n", tokens));
|
||||||
}
|
}
|
||||||
|
|
||||||
let ast = match parse(&tokens, &[]) {
|
let ast = match T::parse(tokens) {
|
||||||
Ok(ast) => ast,
|
Ok(ast) => ast,
|
||||||
Err(err) => {
|
Err(err) => {
|
||||||
output.push_str(&format!("Parse error: {:?}\n", err.msg));
|
output.push_str(&format!("Parse error: {:?}\n", err.msg));
|
||||||
@ -174,12 +179,15 @@ impl<'a> Repl<'a> {
|
|||||||
output.push_str(&format!("AST: {:?}\n", ast));
|
output.push_str(&format!("AST: {:?}\n", ast));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
if self.show_llvm_ir {
|
if self.show_llvm_ir {
|
||||||
let s = compile_ast(ast);
|
let s = compile_ast(ast);
|
||||||
output.push_str(&s);
|
output.push_str(&s);
|
||||||
|
*/
|
||||||
|
if false {
|
||||||
} else {
|
} else {
|
||||||
// for now only handle last output
|
// for now only handle last output
|
||||||
let mut full_output: Vec<String> = self.evaluator.run(ast);
|
let mut full_output: Vec<String> = T::evaluate(ast, &mut self.evaluator);
|
||||||
output.push_str(&full_output.pop().unwrap_or("".to_string()));
|
output.push_str(&full_output.pop().unwrap_or("".to_string()));
|
||||||
}
|
}
|
||||||
output
|
output
|
||||||
@ -239,7 +247,7 @@ impl<'a> Repl<'a> {
|
|||||||
|
|
||||||
struct Schala { }
|
struct Schala { }
|
||||||
|
|
||||||
impl ProgrammingLanguage for Schala {
|
impl<'a> ProgrammingLanguage<eval::Evaluator<'a>> for Schala {
|
||||||
type Token = tokenizer::Token;
|
type Token = tokenizer::Token;
|
||||||
type AST = parser::AST;
|
type AST = parser::AST;
|
||||||
|
|
||||||
@ -250,8 +258,8 @@ impl ProgrammingLanguage for Schala {
|
|||||||
fn parse(input: Vec<Self::Token>) -> Result<Self::AST, ParseError> {
|
fn parse(input: Vec<Self::Token>) -> Result<Self::AST, ParseError> {
|
||||||
parser::parse(&input, &[]).map_err(|x| ParseError { msg: x.msg })
|
parser::parse(&input, &[]).map_err(|x| ParseError { msg: x.msg })
|
||||||
}
|
}
|
||||||
fn evaluate(input: &Self::AST) {
|
fn evaluate(input: Self::AST, evaluator: &mut Evaluator) -> Vec<String> {
|
||||||
unimplemented!()
|
evaluator.run(input)
|
||||||
}
|
}
|
||||||
fn compile(input: &Self::AST) {
|
fn compile(input: &Self::AST) {
|
||||||
unimplemented!()
|
unimplemented!()
|
||||||
|
Loading…
Reference in New Issue
Block a user