awe 0.0.1

reserved for future use
Documentation
use std::iter::Peekable;
use std::str::Chars;

#[derive(Debug, PartialEq)]
pub enum Token {
    Ident,
    Int(u32),
    Float(f64),
    Char(char),
    Str(String),

    Add,
    Sub,
    Mul,
    Div,
    Mod,
    Pow,


}

pub struct Lexer<'a> {
    input: &'a str,
    chars: Peekable<Chars<'a>>,
    current: Option<char>,
    position: usize,
}

impl<'a> Lexer<'a> {
    pub fn new(input: &'a str) -> Self {
        Self {
            input,
            chars: input.chars().peekable(),
            current: None,
            position: 0,
        }
    }

    fn skip_whitespace(&mut self) {
        // println!("skip whitespace");

        while let Some(ch) = self.current {
            if ch.is_whitespace() {
                self.advance();
            } else {
                break;
            }
        }
    }

    fn advance(&mut self) {
        self.current = self.chars.next();
        self.position += 1;
    }

    fn int(&mut self) -> Option<Token> {
        let position = self.position;

        while let Some(ch) = self.current {
            // dbg!(ch);
            if ch.is_digit(10) {
                self.advance();
            } else {
                break;
            }
        }

        let s = &self.input[position..self.position + 1];

        dbg!(&s);

        Some(Token::Int(s.parse().unwrap()))
    }
}

impl Iterator for Lexer<'_> {
    type Item = Token;

    fn next(&mut self) -> Option<Token> {

        self.advance();

        self.skip_whitespace();


        self.current.and_then(|ch| {
            match ch {
                ch if ch.is_digit(10) => self.int(),

                '+' => Some(Token::Add),
                '-' => Some(Token::Sub),
                '*' => Some(Token::Mul),
                '/' => Some(Token::Div),

                ch => {
                    dbg!(ch);
                    todo!()
                },
            }
        })
    }
}


#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn lexer() {
        let input = "1 + 2 / 3";

        let lexer = Lexer::new(input);

        let tokens: Vec<_> = lexer.collect();

        assert_eq!(tokens, vec![
            Token::Int(1),
            Token::Add,
            Token::Int(2),
            Token::Div,
            Token::Int(3),
        ]);
    }
}