diff --git a/mute-interpreter/src/env/core.rs b/mute-interpreter/src/env/core.rs index 33f173f..a978eac 100644 --- a/mute-interpreter/src/env/core.rs +++ b/mute-interpreter/src/env/core.rs @@ -144,16 +144,16 @@ pub(super) fn core() -> HashMap { ( "range", NativeFunc(|mut args| { - let (min, max) = match args.len() { + let (min, max, step) = match args.len() { 0 => return Node::Error("expected at least 1 argument".to_string()), 1 => match args.pop_front().expect("argument length checked above") { - Node::Int(max) => (1, (max as usize)), + Node::Int(max) => (1, (max as usize), 1), node => { return Node::Error(format!("expected int, got {}", node.get_type())) } }, 2 => match (args.pop_front().unwrap(), args.pop_front().unwrap()) { - (Node::Int(min), Node::Int(max)) => (min as usize, max as usize), + (Node::Int(min), Node::Int(max)) => (min as usize, max as usize, 1), (min, max) => { return Node::Error(format!( "expected int and int, got {} and {}", @@ -162,12 +162,33 @@ pub(super) fn core() -> HashMap { )) } }, + 3 => { + match ( + args.pop_front().unwrap(), + args.pop_front().unwrap(), + args.pop_front().unwrap(), + ) { + (Node::Int(min), Node::Int(max), Node::Int(step)) => { + (min as usize, max as usize, step as usize) + } + (min, max, step) => { + return Node::Error(format!( + "expected int and int and int, got {} and {} and {}", + min.get_type(), + max.get_type(), + step.get_type() + )) + } + } + } count => { return Node::Error(format!("expected 1 or 2 arguments, got {}", count)) } }; - let list = VecDeque::from_iter((min..(max + 1)).map(|i| Node::Int(i as i64))); + let list = VecDeque::from_iter( + (min..(max + 1)).step_by(step).map(|i| Node::Int(i as i64)), + ); Node::List(list) }),