From 05c6f24c0b371a465a8735cfd1ac17c0394363cb Mon Sep 17 00:00:00 2001 From: Akshay Date: Wed, 24 Mar 2021 13:05:05 +0530 Subject: allow minus operator, improve display for exprs --- src/lisp/expr.rs | 49 ++++++++++++++++++++++++++----------------------- src/lisp/lex.rs | 7 ++++++- src/lisp/mod.rs | 1 - 3 files changed, 32 insertions(+), 25 deletions(-) diff --git a/src/lisp/expr.rs b/src/lisp/expr.rs index adacc1c..651e41f 100644 --- a/src/lisp/expr.rs +++ b/src/lisp/expr.rs @@ -1,7 +1,30 @@ use std::fmt; use crate::app::AppState; -use crate::lisp::{error::LispError, number::LispNumber}; +use crate::lisp::{error::LispError, number::LispNumber, Environment}; + +#[derive(Clone)] +pub struct PrimitiveFunc { + pub arity: Option, // minimim arity + pub closure: fn(&[LispExpr], &mut AppState) -> Result, +} + +impl PrimitiveFunc { + pub fn call(&self, args: &[LispExpr], app: &mut AppState) -> Result { + if let Some(arity) = self.arity { + if args.len() < arity { + return Err(LispError::EvalError); + } + } + (self.closure)(args, app) + } +} + +#[derive(Clone)] +pub struct LispFunction { + pub params: Vec, + pub body: Vec, +} #[derive(Clone)] pub enum LispExpr { @@ -21,23 +44,6 @@ pub enum LispExpr { Quote(Box, u32), } -#[derive(Clone)] -pub struct PrimitiveFunc { - pub arity: Option, - pub closure: fn(&[LispExpr], &mut AppState) -> Result, -} - -impl PrimitiveFunc { - pub fn call(&self, args: &[LispExpr], app: &mut AppState) -> Result { - if let Some(arity) = self.arity { - if args.len() < arity { - return Err(LispError::EvalError); - } - } - (self.closure)(args, app) - } -} - impl LispExpr { pub fn comma(self, n: u32) -> LispExpr { match self { @@ -83,7 +89,7 @@ impl fmt::Display for LispExpr { write!(f, " {} ", expr)? } } - LispExpr::StringLit(s) => write!(f, "{:?}", s)?, + LispExpr::StringLit(s) => write!(f, "{}", s)?, LispExpr::BoolLit(b) => { if *b { write!(f, "#t")? @@ -93,7 +99,7 @@ impl fmt::Display for LispExpr { } LispExpr::Ident(s) => write!(f, "{}", s)?, LispExpr::PrimitiveFunc(_) => write!(f, "<#primitive>")?, - LispExpr::Function(_) => write!(f, "<#procedure>")?, + LispExpr::Function(func) => write!(f, "<#lambda {}>", func.params.join(" "))?, LispExpr::Quasiquote(val, depth) => { write!(f, "{}{}", "`".repeat(*depth as usize), val)? } @@ -104,6 +110,3 @@ impl fmt::Display for LispExpr { Ok(()) } } - -#[derive(Debug, PartialEq, Clone)] -enum LispFunction {} diff --git a/src/lisp/lex.rs b/src/lisp/lex.rs index 30f49fa..a7b9586 100644 --- a/src/lisp/lex.rs +++ b/src/lisp/lex.rs @@ -115,11 +115,13 @@ impl<'a> Lexer<'a> { fn parse_number<'a>(mut input: &'a str) -> Result<(usize, Token<'a>), LispError> { let mut dot = false; + let mut minus = false; let mut size = 0; let mut chars = input.chars(); if let Some(v) = chars.next() { if v == '-' { + minus = true; size += 1; input = &input[1..]; } else if v.is_digit(10) { @@ -143,7 +145,10 @@ fn parse_number<'a>(mut input: &'a str) -> Result<(usize, Token<'a>), LispError> return Err(LispError::ParseError); } } - let tok = if dot { + + let tok = if size == 1 && minus { + Token::Name("-") + } else if dot { Token::Float(&input[..size]) } else { Token::Integer(&input[..size]) diff --git a/src/lisp/mod.rs b/src/lisp/mod.rs index 2a19314..dc08835 100644 --- a/src/lisp/mod.rs +++ b/src/lisp/mod.rs @@ -4,7 +4,6 @@ pub mod expr; pub mod lex; pub mod number; pub mod parse; -#[macro_use] mod primitives; use std::collections::HashMap; -- cgit v1.2.3