From 7864e4271c392639dcc4021cc3f46f803523d3e7 Mon Sep 17 00:00:00 2001 From: cmontella Date: Tue, 30 Jul 2024 00:26:46 -0400 Subject: [PATCH 01/14] implement index all, ":" --- src/syntax/src/interpreter.rs | 2 +- src/syntax/src/matrix.rs | 2 +- src/syntax/src/stdlib/matrix.rs | 104 +++++++++++++++++++++++++++++--- src/syntax/src/value.rs | 5 ++ src/syntax/tests/interpreter.rs | 5 +- 5 files changed, 105 insertions(+), 13 deletions(-) diff --git a/src/syntax/src/interpreter.rs b/src/syntax/src/interpreter.rs index a72bc72..c55b086 100644 --- a/src/syntax/src/interpreter.rs +++ b/src/syntax/src/interpreter.rs @@ -374,7 +374,7 @@ fn subscript(sbscrpt: &Subscript, val: &Value, plan: Plan, symbols: SymbolTableR Ok(res) }, Subscript::Brace(x) => todo!(), - Subscript::All => todo!(), + Subscript::All => Ok(Value::IndexAll), } } diff --git a/src/syntax/src/matrix.rs b/src/syntax/src/matrix.rs index f9dfe81..6636a93 100644 --- a/src/syntax/src/matrix.rs +++ b/src/syntax/src/matrix.rs @@ -22,7 +22,7 @@ macro_rules! impl_to_matrix { match (rows,cols) { (1,1) => Matrix::Matrix1(new_ref(Matrix1::from_element(elements[0].clone()))), (2,2) => Matrix::Matrix2(new_ref(Matrix2::from_vec(elements))), - (3,4) => Matrix::Matrix3(new_ref(Matrix3::from_vec(elements))), + (3,3) => Matrix::Matrix3(new_ref(Matrix3::from_vec(elements))), (4,2) => Matrix::Matrix4(new_ref(Matrix4::from_vec(elements))), (2,3) => Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(elements))), (3,2) => Matrix::Matrix3x2(new_ref(Matrix3x2::from_vec(elements))), diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index bd05e49..ba20b65 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -225,6 +225,33 @@ macro_rules! access_2d_slice2 { } };} +macro_rules! access_col { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + for i in 0..(*$source).nrows() { + (*$out)[i] = (*$source).index((i,*$ix-1)).clone(); + } + } + };} + +macro_rules! access_row { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + for i in 0..(*$source).nrows() { + (*$out)[i] = (*$source).index((*$ix-1,i)).clone(); + } + } + };} + +macro_rules! access_1d_all { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + for i in 0..(*$source).len() { + (*$out)[i] = (*$source).index(i).clone(); + } + } + };} + macro_rules! impl_access_fxn { ($struct_name:ident, $arg_type:ty, $ix_type:ty, $out_type:ty, $op:ident) => { #[derive(Debug)] @@ -248,6 +275,7 @@ macro_rules! impl_access_fxn { fn to_string(&self) -> String { format!("{:?}", self) } }};} +// x[1] impl_access_fxn!(Access1DSR2, RowVector2, usize, T, access_1d); impl_access_fxn!(Access1DSR3, RowVector3, usize, T, access_1d); impl_access_fxn!(Access1DSR4, RowVector4, usize, T, access_1d); @@ -259,6 +287,7 @@ impl_access_fxn!(Access1DSMD, DMatrix, usize, T, access_1d); impl_access_fxn!(Access1DSRD, RowDVector, usize, T, access_1d); impl_access_fxn!(Access1DSVD, DVector, usize, T, access_1d); +// x[1,2] impl_access_fxn!(Access2DSR2, RowVector2, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSR3, RowVector3, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSR4, RowVector4, (usize,usize), T, access_2d); @@ -270,16 +299,35 @@ impl_access_fxn!(Access2DSMD, DMatrix, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSRD, RowDVector, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSVD, DVector, (usize,usize), T, access_2d); +// x[1..3] impl_access_fxn!(Access1DR2RD, RowDVector, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR3RD, RowDVector, RowVector3, RowVector3, access_1d_slice3); + +// x[1..3,1..3] impl_access_fxn!(Access2DR2M3, Matrix3, (RowVector2,RowVector2), Matrix2, access_2d_slice2); impl_access_fxn!(Access2DR2DM, DMatrix, (RowVector2,RowVector2), Matrix2, access_2d_slice2); +// x[:] +impl_access_fxn!(Access1DAM2, Matrix2, Value, Vector4, access_1d_all); +impl_access_fxn!(Access1DAM3, Matrix3, Value, DVector, access_1d_all); +impl_access_fxn!(Access1DAMD, DMatrix, Value, DVector, access_1d_all); + +// x[:,1] +impl_access_fxn!(Access2DASM2, Matrix2, usize, Vector2, access_col); +impl_access_fxn!(Access2DASM3, Matrix3, usize, Vector3, access_col); +impl_access_fxn!(Access2DASMD, DMatrix, usize, DVector, access_col); + +// x[1,:] +impl_access_fxn!(Access2DSAM2, Matrix2, usize, RowVector2, access_row); +impl_access_fxn!(Access2DSAM3, Matrix3, usize, RowVector3, access_row); +impl_access_fxn!(Access2DSAMD, DMatrix, usize, RowDVector, access_row); + macro_rules! generate_access_match_arms { ($arg:expr, $($input_type:ident => $($matrix_kind:ident, $target_type:ident, $default:expr),+);+ $(;)?) => { match $arg { $( $( + // x[1] (Value::$matrix_kind(Matrix::<$target_type>::RowVector4(input)), [Value::Index(ix)]) => { Ok(Box::new(Access1DSR4{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) }, @@ -310,32 +358,68 @@ macro_rules! generate_access_match_arms { (Value::$matrix_kind(Matrix::<$target_type>::DVector(input)), [Value::Index(ix)]) => { Ok(Box::new(Access1DSVD{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) }, + // x[1,2] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::Index(ix1),Value::Index(ix2)]) => { + Ok(Box::new(Access2DSM2{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::Index(ix1),Value::Index(ix2)]) => { + Ok(Box::new(Access2DSM3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2x3(input)), [Value::Index(ix1),Value::Index(ix2)]) => { + Ok(Box::new(Access2DSM2x3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3x2(input)), [Value::Index(ix1),Value::Index(ix2)]) => { + Ok(Box::new(Access2DSM3x2{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::Index(ix1),Value::Index(ix2)]) => { + Ok(Box::new(Access2DSMD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + }, + // x[1..3] (Value::$matrix_kind(Matrix::<$target_type>::RowDVector(input)), [Value::MatrixIndex(Matrix::RowVector2(ix))]) => { Ok(Box::new(Access1DR2RD{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::RowDVector(input)), [Value::MatrixIndex(Matrix::RowVector3(ix))]) => { Ok(Box::new(Access1DR3RD{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector3::from_element($default)) })) }, + // x[1..3,1..3] (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::MatrixIndex(Matrix::RowVector2(ix1)), Value::MatrixIndex(Matrix::RowVector2(ix2))]) => { Ok(Box::new(Access2DR2M3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::MatrixIndex(Matrix::RowVector2(ix1)), Value::MatrixIndex(Matrix::RowVector2(ix2))]) => { Ok(Box::new(Access2DR2DM{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) }, - (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::Index(ix1),Value::Index(ix2)]) => { - Ok(Box::new(Access2DSM2{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + // x[:] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll]) => { + Ok(Box::new(Access1DAM3{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(9,$default)) })) }, - (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::Index(ix1),Value::Index(ix2)]) => { - Ok(Box::new(Access2DSM3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::IndexAll]) => { + Ok(Box::new(Access1DAM2{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(Vector4::from_element($default)) })) }, - (Value::$matrix_kind(Matrix::<$target_type>::Matrix2x3(input)), [Value::Index(ix1),Value::Index(ix2)]) => { - Ok(Box::new(Access2DSM2x3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::IndexAll]) => { + let len = input.borrow().len(); + Ok(Box::new(Access1DAMD{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(len,$default)) })) }, - (Value::$matrix_kind(Matrix::<$target_type>::Matrix3x2(input)), [Value::Index(ix1),Value::Index(ix2)]) => { - Ok(Box::new(Access2DSM3x2{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + // x[:,2] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::IndexAll,Value::Index(ix)]) => { + Ok(Box::new(Access2DASM2{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector2::from_element($default)) })) }, - (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::Index(ix1),Value::Index(ix2)]) => { - Ok(Box::new(Access2DSMD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll,Value::Index(ix)]) => { + Ok(Box::new(Access2DASM3{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector3::from_element($default)) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::IndexAll,Value::Index(ix)]) => { + let len = input.borrow().nrows(); + Ok(Box::new(Access2DASMD{source: input.clone(), ixes: ix.clone(), out: new_ref(DVector::from_element(len,$default)) })) + }, + // x[2,:] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::Index(ix),Value::IndexAll]) => { + Ok(Box::new(Access2DSAM2{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::Index(ix),Value::IndexAll]) => { + Ok(Box::new(Access2DSAM3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector3::from_element($default)) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::Index(ix),Value::IndexAll]) => { + let len = input.borrow().ncols(); + Ok(Box::new(Access2DSAMD{source: input.clone(), ixes: ix.clone(), out: new_ref(RowDVector::from_element(len,$default)) })) }, )+ )+ diff --git a/src/syntax/src/value.rs b/src/syntax/src/value.rs index a608508..6248af2 100644 --- a/src/syntax/src/value.rs +++ b/src/syntax/src/value.rs @@ -62,6 +62,7 @@ pub enum Value { Index(Ref), MutableReference(MutableReference), Kind(ValueKind), + IndexAll, Empty } @@ -107,6 +108,7 @@ impl Hash for Value { Value::MatrixF64(x) => x.hash(state), Value::MutableReference(x) => x.borrow().hash(state), Value::Empty => Value::Empty.hash(state), + Value::IndexAll => Value::IndexAll.hash(state), } } } @@ -153,6 +155,7 @@ impl Value { Value::MatrixF64(x) => {return x.pretty_print();}, Value::MutableReference(x) => {return x.borrow().pretty_print();}, Value::Empty => builder.push_record(vec!["_"]), + Value::IndexAll => builder.push_record(vec![":"]), _ => unreachable!(), }; let mut table = builder.build(); @@ -199,6 +202,7 @@ impl Value { Value::Tuple(x) => vec![1,x.size()], Value::MutableReference(x) => vec![1,1], Value::Empty => vec![0,0], + Value::IndexAll => vec![0,0], Value::Kind(_) => vec![0,0], Value::Id(x) => vec![0,0], } @@ -242,6 +246,7 @@ impl Value { Value::Tuple(x) => ValueKind::Tuple, Value::MutableReference(x) => ValueKind::Reference, Value::Empty => ValueKind::Empty, + Value::IndexAll => ValueKind::Empty, Value::Id(x) => ValueKind::Id, Value::Index(x) => ValueKind::Index, Value::Kind(x) => x.clone(), diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 4150132..d55f3ff 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -9,7 +9,7 @@ use std::rc::Rc; use mech_syntax::matrix::Matrix; use mech_syntax::*; use indexmap::set::IndexSet; -use na::{Vector3, DVector, RowDVector, Matrix1, Matrix3, Matrix4, RowVector3, RowVector4, RowVector2, DMatrix, Rotation3, Matrix3x2, Matrix2x3, Matrix6, Matrix2}; +use na::{Vector3, DVector, RowDVector, Matrix1, Matrix3, Matrix4, RowVector3, RowVector4, RowVector2, Vector4, Vector2, DMatrix, Rotation3, Matrix3x2, Matrix2x3, Matrix6, Matrix2}; /// Compare interpreter output to expected value macro_rules! test_interpreter { @@ -130,6 +130,9 @@ test_interpreter!(interpret_slice_f64, "a := [1.0,2.0,3.0]; a[2]", Value::F64(ne test_interpreter!(interpret_slice_2d_f64, "a := [1,2;3,4]; a[2,1]", Value::I64(new_ref(3))); test_interpreter!(interpret_slice_range, "x := 4..10; x[1..=3]", Value::MatrixI64(Matrix::RowVector3(new_ref(RowVector3::from_vec(vec![4,5,6]))))); test_interpreter!(interpret_slice_range_2d, "x := [1 2 3; 4 5 6; 7 8 9]; x[2..=3, 2..=3]", Value::MatrixI64(Matrix::Matrix2(new_ref(Matrix2::from_vec(vec![5,8,6,9]))))); +test_interpreter!(interpret_slice_all, "x := [1 2; 4 5]; x[:]", Value::MatrixI64(Matrix::Vector4(new_ref(Vector4::from_vec(vec![1,4,2,5]))))); +test_interpreter!(interpret_slice_all_2d, "x := [1 2; 4 5]; x[:,2]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![2,5]))))); +test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![4,5]))))); test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); From f5b3808dd64a2917528438b37ecb15f36b946b9b Mon Sep 17 00:00:00 2001 From: cmontella Date: Tue, 30 Jul 2024 16:30:45 -0400 Subject: [PATCH 02/14] More slicing --- src/syntax/src/stdlib/matrix.rs | 65 ++++++++++++++++++++++++++++----- src/syntax/tests/interpreter.rs | 2 + 2 files changed, 57 insertions(+), 10 deletions(-) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index ba20b65..0d14974 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -212,8 +212,7 @@ macro_rules! access_1d_slice3 { (*$out)[0] = (*$source).index((*$ix)[0]-1).clone(); (*$out)[1] = (*$source).index((*$ix)[1]-1).clone(); (*$out)[2] = (*$source).index((*$ix)[2]-1).clone(); - } - };} + }};} macro_rules! access_2d_slice2 { ($source:expr, $ix:expr, $out:expr) => { @@ -222,8 +221,33 @@ macro_rules! access_2d_slice2 { (*$out)[1] = (*$source).index(((*$ix).0[1]-1,(*$ix).1[0]-1)).clone(); (*$out)[2] = (*$source).index(((*$ix).0[0]-1,(*$ix).1[1]-1)).clone(); (*$out)[3] = (*$source).index(((*$ix).0[1]-1,(*$ix).1[1]-1)).clone(); - } - };} + }};} + +macro_rules! access_2d_slice2_all { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + let n_cols = (*$out).ncols(); + let mut out_ix = 0; + for i in 0..n_cols { + (*$out)[out_ix] = (*$source).index(((*$ix)[0] - 1, i)).clone(); + out_ix += 1; + (*$out)[out_ix] = (*$source).index(((*$ix)[1] - 1, i)).clone(); + out_ix += 1; + }}};} + +macro_rules! access_2d_all_slice2 { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + let n_rows = (*$source).nrows(); + let n_cols = (*$ix).ncols(); + let mut out_ix = 0; + for c in 0..n_cols { + for r in 0..n_rows { + (*$out)[out_ix] = (*$source).index((r,(*$ix)[c] - 1)).clone(); + out_ix += 1; + } + } + }};} macro_rules! access_col { ($source:expr, $ix:expr, $out:expr) => { @@ -231,8 +255,7 @@ macro_rules! access_col { for i in 0..(*$source).nrows() { (*$out)[i] = (*$source).index((i,*$ix-1)).clone(); } - } - };} + }};} macro_rules! access_row { ($source:expr, $ix:expr, $out:expr) => { @@ -240,8 +263,7 @@ macro_rules! access_row { for i in 0..(*$source).nrows() { (*$out)[i] = (*$source).index((*$ix-1,i)).clone(); } - } - };} + }};} macro_rules! access_1d_all { ($source:expr, $ix:expr, $out:expr) => { @@ -249,8 +271,7 @@ macro_rules! access_1d_all { for i in 0..(*$source).len() { (*$out)[i] = (*$source).index(i).clone(); } - } - };} + }};} macro_rules! impl_access_fxn { ($struct_name:ident, $arg_type:ty, $ix_type:ty, $out_type:ty, $op:ident) => { @@ -322,6 +343,16 @@ impl_access_fxn!(Access2DSAM2, Matrix2, usize, RowVector2, access_row); impl_access_fxn!(Access2DSAM3, Matrix3, usize, RowVector3, access_row); impl_access_fxn!(Access2DSAMD, DMatrix, usize, RowDVector, access_row); +// x[1..3,:] +impl_access_fxn!(Access2DR2AMD, DMatrix, RowVector2, DMatrix, access_2d_slice2_all); +impl_access_fxn!(Access2DR2AM3, Matrix3, RowVector2, Matrix2x3, access_2d_slice2_all); + + +// x[:,1..3] +impl_access_fxn!(Access2DAR2MD, DMatrix, RowVector2, DMatrix, access_2d_all_slice2); + +// x.x,y,z + macro_rules! generate_access_match_arms { ($arg:expr, $($input_type:ident => $($matrix_kind:ident, $target_type:ident, $default:expr),+);+ $(;)?) => { match $arg { @@ -421,6 +452,20 @@ macro_rules! generate_access_match_arms { let len = input.borrow().ncols(); Ok(Box::new(Access2DSAMD{source: input.clone(), ixes: ix.clone(), out: new_ref(RowDVector::from_element(len,$default)) })) }, + // x[1..3,:] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::MatrixIndex(Matrix::RowVector2(ix)), Value::IndexAll]) => { + let cols = input.borrow().ncols(); + Ok(Box::new(Access2DR2AM3{source: input.clone(), ixes: ix.clone(), out: new_ref(Matrix2x3::from_element($default)) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::MatrixIndex(Matrix::RowVector2(ix)), Value::IndexAll]) => { + let cols = input.borrow().ncols(); + Ok(Box::new(Access2DR2AMD{source: input.clone(), ixes: ix.clone(), out: new_ref(DMatrix::from_element(2,cols,$default)) })) + }, + // x[:,1..3] + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::IndexAll, Value::MatrixIndex(Matrix::RowVector2(ix))]) => { + let rows = input.borrow().nrows(); + Ok(Box::new(Access2DAR2MD{source: input.clone(), ixes: ix.clone(), out: new_ref(DMatrix::from_element(rows,2,$default)) })) + }, )+ )+ x => Err(MechError { tokens: vec![], msg: format!("{:?}",x), id: 314, kind: MechErrorKind::UnhandledFunctionArgumentKind }), diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index d55f3ff..cdf12b0 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -133,6 +133,8 @@ test_interpreter!(interpret_slice_range_2d, "x := [1 2 3; 4 5 6; 7 8 9]; x[2..=3 test_interpreter!(interpret_slice_all, "x := [1 2; 4 5]; x[:]", Value::MatrixI64(Matrix::Vector4(new_ref(Vector4::from_vec(vec![1,4,2,5]))))); test_interpreter!(interpret_slice_all_2d, "x := [1 2; 4 5]; x[:,2]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![2,5]))))); test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![4,5]))))); +test_interpreter!(interpret_slice_all_range, "x := [1 2 3 4; 5 6 7 8]; x[:,1..=2]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,2,vec![1,5,2,6]))))); +test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,4,2,5,3,6]))))); test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); From 437bc77a58bd597c647496a09b9de428913e1e42 Mon Sep 17 00:00:00 2001 From: cmontella Date: Wed, 31 Jul 2024 02:03:04 -0400 Subject: [PATCH 03/14] Allow i64 to be used as an index --- src/syntax/src/matrix.rs | 3 ++- src/syntax/src/value.rs | 12 ++++++++---- src/syntax/tests/interpreter.rs | 1 + 3 files changed, 11 insertions(+), 5 deletions(-) diff --git a/src/syntax/src/matrix.rs b/src/syntax/src/matrix.rs index 6636a93..768eb49 100644 --- a/src/syntax/src/matrix.rs +++ b/src/syntax/src/matrix.rs @@ -36,7 +36,8 @@ macro_rules! impl_to_matrix { (m,1) => Matrix::DVector(new_ref(DVector::from_vec(elements))), (m,n) => Matrix::DMatrix(new_ref(DMatrix::from_vec(m,n,elements))), }}}};} - + +impl_to_matrix!(usize); impl_to_matrix!(bool); impl_to_matrix!(u8); impl_to_matrix!(u16); diff --git a/src/syntax/src/value.rs b/src/syntax/src/value.rs index 6248af2..91c5b46 100644 --- a/src/syntax/src/value.rs +++ b/src/syntax/src/value.rs @@ -290,10 +290,14 @@ impl Value { pub fn as_index(&self) -> MResult { match self.as_usize() { Some(ix) => Ok(Value::Index(new_ref(ix))), - None => match self { - //Value::MatrixI64(x) => Ok(x.as_index()?), - _ => todo!(), - }, + None => match self.as_vecusize() { + Some(x) => { + let shape = self.shape(); + let out = Value::MatrixIndex(usize::to_matrix(x, shape[0], shape[1])); + Ok(out) + }, + None => Err(MechError {tokens: vec![], msg: file!().to_string(), id: line!(), kind: MechErrorKind::UnhandledIndexKind}), + } } } diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index cdf12b0..b696b9e 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -135,6 +135,7 @@ test_interpreter!(interpret_slice_all_2d, "x := [1 2; 4 5]; x[:,2]", Value::Matr test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![4,5]))))); test_interpreter!(interpret_slice_all_range, "x := [1 2 3 4; 5 6 7 8]; x[:,1..=2]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,2,vec![1,5,2,6]))))); test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,4,2,5,3,6]))))); +test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,1,2,2,3,3]))))); test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); From dc9373bae3a54d016f9abaf51c8cb5373b9c5672 Mon Sep 17 00:00:00 2001 From: cmontella Date: Wed, 31 Jul 2024 14:26:14 -0400 Subject: [PATCH 04/14] implement more access patterns --- src/syntax/src/stdlib/matrix.rs | 9 +++++++++ src/syntax/tests/interpreter.rs | 3 +++ 2 files changed, 12 insertions(+) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index 0d14974..b7e8d7b 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -329,6 +329,7 @@ impl_access_fxn!(Access2DR2M3, Matrix3, (RowVector2,RowVector2) impl_access_fxn!(Access2DR2DM, DMatrix, (RowVector2,RowVector2), Matrix2, access_2d_slice2); // x[:] +impl_access_fxn!(Access1DAM3x2, Matrix3x2, Value, DVector, access_1d_all); impl_access_fxn!(Access1DAM2, Matrix2, Value, Vector4, access_1d_all); impl_access_fxn!(Access1DAM3, Matrix3, Value, DVector, access_1d_all); impl_access_fxn!(Access1DAMD, DMatrix, Value, DVector, access_1d_all); @@ -350,6 +351,7 @@ impl_access_fxn!(Access2DR2AM3, Matrix3, RowVector2, Matrix2x3, acc // x[:,1..3] impl_access_fxn!(Access2DAR2MD, DMatrix, RowVector2, DMatrix, access_2d_all_slice2); +impl_access_fxn!(Access2DAR2M3, Matrix3, RowVector2, Matrix3x2, access_2d_all_slice2); // x.x,y,z @@ -420,6 +422,9 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access2DR2DM{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) }, // x[:] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3x2(input)), [Value::IndexAll]) => { + Ok(Box::new(Access1DAM3x2{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(6,$default)) })) + }, (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll]) => { Ok(Box::new(Access1DAM3{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(9,$default)) })) }, @@ -466,6 +471,10 @@ macro_rules! generate_access_match_arms { let rows = input.borrow().nrows(); Ok(Box::new(Access2DAR2MD{source: input.clone(), ixes: ix.clone(), out: new_ref(DMatrix::from_element(rows,2,$default)) })) }, + // x[:,1..3] + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll, Value::MatrixIndex(Matrix::RowVector2(ix))]) => { + Ok(Box::new(Access2DAR2M3{source: input.clone(), ixes: ix.clone(), out: new_ref(Matrix3x2::from_element($default)) })) + }, )+ )+ x => Err(MechError { tokens: vec![], msg: format!("{:?}",x), id: 314, kind: MechErrorKind::UnhandledFunctionArgumentKind }), diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index b696b9e..4f169d5 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -136,6 +136,9 @@ test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value:: test_interpreter!(interpret_slice_all_range, "x := [1 2 3 4; 5 6 7 8]; x[:,1..=2]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,2,vec![1,5,2,6]))))); test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,4,2,5,3,6]))))); test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,1,2,2,3,3]))))); +test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := x[:,[1,1]]; y[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,7,1,4,7]))))); + + test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); From fae70569aa5dfb6bf37b7b993aedde0417eddf7f Mon Sep 17 00:00:00 2001 From: cmontella Date: Thu, 1 Aug 2024 01:20:55 -0400 Subject: [PATCH 05/14] Implement ix variables --- src/bin/mech.rs | 6 ++++++ src/syntax/src/stdlib/matrix.rs | 4 ++++ src/syntax/src/value.rs | 3 ++- src/syntax/tests/interpreter.rs | 1 + 4 files changed, 13 insertions(+), 1 deletion(-) diff --git a/src/bin/mech.rs b/src/bin/mech.rs index 76f0e6b..3385694 100644 --- a/src/bin/mech.rs +++ b/src/bin/mech.rs @@ -139,11 +139,17 @@ fn main() -> Result<(), MechError> { io::stdin().read_line(&mut input).unwrap(); match parser::parse(&input) { Ok(tree) => { + let now = Instant::now(); let result = intrp.interpret(&tree); + let elapsed_time = now.elapsed(); + let cycle_duration = elapsed_time.as_nanos() as f64; + match result { Ok(r) => println!("{}", r.pretty_print()), Err(err) => println!("{:?}", err), } + println!("{:0.2?} ns", cycle_duration / 1000000.0); + } Err(err) => { if let MechErrorKind::ParserError(report, _) = err.kind { diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index b7e8d7b..3154c3c 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -321,6 +321,7 @@ impl_access_fxn!(Access2DSRD, RowDVector, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSVD, DVector, (usize,usize), T, access_2d); // x[1..3] +impl_access_fxn!(Access1DR2R3, RowVector3, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR2RD, RowDVector, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR3RD, RowDVector, RowVector3, RowVector3, access_1d_slice3); @@ -408,6 +409,9 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access2DSMD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) }, // x[1..3] + (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), [Value::MatrixIndex(Matrix::RowVector2(ix))]) => { + Ok(Box::new(Access1DR2R3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) + }, (Value::$matrix_kind(Matrix::<$target_type>::RowDVector(input)), [Value::MatrixIndex(Matrix::RowVector2(ix))]) => { Ok(Box::new(Access1DR2RD{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) }, diff --git a/src/syntax/src/value.rs b/src/syntax/src/value.rs index 91c5b46..507af40 100644 --- a/src/syntax/src/value.rs +++ b/src/syntax/src/value.rs @@ -200,7 +200,7 @@ impl Value { Value::Map(x) => vec![1,x.map.len()], Value::Record(x) => vec![1,x.map.len()], Value::Tuple(x) => vec![1,x.size()], - Value::MutableReference(x) => vec![1,1], + Value::MutableReference(x) => x.borrow().shape(), Value::Empty => vec![0,0], Value::IndexAll => vec![0,0], Value::Kind(_) => vec![0,0], @@ -283,6 +283,7 @@ impl Value { match self { Value::MatrixIndex(v) => Some(v.as_vec()), Value::MatrixI64(v) => Some(v.as_vec().iter().map(|x| *x as usize).collect::>()), + Value::MutableReference(x) => x.borrow().as_vecusize(), _ => todo!(), } } diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 4f169d5..356edc3 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -137,6 +137,7 @@ test_interpreter!(interpret_slice_all_range, "x := [1 2 3 4; 5 6 7 8]; x[:,1..=2 test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,4,2,5,3,6]))))); test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,1,2,2,3,3]))))); test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := x[:,[1,1]]; y[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,7,1,4,7]))))); +test_interpreter!(interpret_slice_ix_ref, "x := [94 53 13]; y := [3 3]; x[y]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![13,13]))))); From 08ac20529b387e4b88ee49078ea32e860e94a309 Mon Sep 17 00:00:00 2001 From: cmontella Date: Thu, 1 Aug 2024 16:09:12 -0400 Subject: [PATCH 06/14] Implement more shapes --- src/syntax/src/stdlib/matrix.rs | 4 ++++ src/syntax/tests/interpreter.rs | 1 + 2 files changed, 5 insertions(+) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index 3154c3c..51f77d6 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -321,6 +321,7 @@ impl_access_fxn!(Access2DSRD, RowDVector, (usize,usize), T, access_2d); impl_access_fxn!(Access2DSVD, DVector, (usize,usize), T, access_2d); // x[1..3] +impl_access_fxn!(Access1DV2R3, RowVector3, Vector2, Vector2, access_1d_slice2); impl_access_fxn!(Access1DR2R3, RowVector3, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR2RD, RowDVector, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR3RD, RowDVector, RowVector3, RowVector3, access_1d_slice3); @@ -409,6 +410,9 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access2DSMD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) }, // x[1..3] + (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), [Value::MatrixIndex(Matrix::Vector2(ix))]) => { + Ok(Box::new(Access1DV2R3{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector2::from_element($default)) })) + }, (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), [Value::MatrixIndex(Matrix::RowVector2(ix))]) => { Ok(Box::new(Access1DR2R3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) }, diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 356edc3..60f539a 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -138,6 +138,7 @@ test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..= test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,1,2,2,3,3]))))); test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := x[:,[1,1]]; y[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,7,1,4,7]))))); test_interpreter!(interpret_slice_ix_ref, "x := [94 53 13]; y := [3 3]; x[y]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![13,13]))))); +test_interpreter!(interpret_slice_ix_ref2, "x := [94 53 13]; y := [3; 3]; x[y]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![13,13]))))); From 728e8f9cccb373cc4222b5bf02c5c2c9f1fde2c4 Mon Sep 17 00:00:00 2001 From: cmontella Date: Thu, 1 Aug 2024 16:28:00 -0400 Subject: [PATCH 07/14] scalar ixes --- src/syntax/src/value.rs | 1 + src/syntax/tests/interpreter.rs | 4 +--- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/src/syntax/src/value.rs b/src/syntax/src/value.rs index 507af40..75f9320 100644 --- a/src/syntax/src/value.rs +++ b/src/syntax/src/value.rs @@ -317,6 +317,7 @@ impl Value { Value::I128(v) => Some(*v.borrow() as usize), Value::F32(v) => Some((*v.borrow()).0 as usize), Value::F64(v) => Some((*v.borrow()).0 as usize), + Value::MutableReference(v) => v.borrow().as_usize(), _ => None, } } diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 60f539a..e7cbff2 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -139,9 +139,7 @@ test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := x[:,[1,1]]; y[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,7,1,4,7]))))); test_interpreter!(interpret_slice_ix_ref, "x := [94 53 13]; y := [3 3]; x[y]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![13,13]))))); test_interpreter!(interpret_slice_ix_ref2, "x := [94 53 13]; y := [3; 3]; x[y]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![13,13]))))); - - - +test_interpreter!(interpret_slice_ix_ref3, "x := [94 53 13]; y := 3; x[y]", Value::I64(new_ref(13))); test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); test_interpreter!(interpret_set,"{1,2,3}", Value::Set(MechSet::from_vec(vec![Value::I64(new_ref(1)),Value::I64(new_ref(2)),Value::I64(new_ref(3))]))); From 23f6ec8d97edc84b9e34ebc7b4465fdc0ccc18ed Mon Sep 17 00:00:00 2001 From: cmontella Date: Thu, 1 Aug 2024 23:18:21 -0400 Subject: [PATCH 08/14] logical indexing is back! --- src/syntax/src/stdlib/matrix.rs | 27 +++++++++++++++++++++++++++ src/syntax/src/value.rs | 10 +++++++++- src/syntax/tests/interpreter.rs | 2 ++ 3 files changed, 38 insertions(+), 1 deletion(-) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index 51f77d6..e3b43bd 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -214,6 +214,28 @@ macro_rules! access_1d_slice3 { (*$out)[2] = (*$source).index((*$ix)[2]-1).clone(); }};} +macro_rules! access_1d_slice_bool { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + let mut j = 0; + let out_len = (*$out).len(); + for i in 0..(*$ix).len() { + if (*$ix)[i] == true { + j += 1; + } + } + if j != out_len { + (*$out).resize_horizontally_mut(j,(*$out)[0]); + } + j = 0; + for i in 0..(*$source).len() { + if (*$ix)[i] == true { + (*$out)[j] = (*$source).index(i).clone(); + j += 1; + } + } + }};} + macro_rules! access_2d_slice2 { ($source:expr, $ix:expr, $out:expr) => { unsafe { @@ -325,6 +347,7 @@ impl_access_fxn!(Access1DV2R3, RowVector3, Vector2, Vector2, access impl_access_fxn!(Access1DR2R3, RowVector3, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR2RD, RowDVector, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn!(Access1DR3RD, RowDVector, RowVector3, RowVector3, access_1d_slice3); +impl_access_fxn!(Access1DR3bR3, RowVector3, RowVector3, RowDVector, access_1d_slice_bool); // x[1..3,1..3] impl_access_fxn!(Access2DR2M3, Matrix3, (RowVector2,RowVector2), Matrix2, access_2d_slice2); @@ -410,6 +433,10 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access2DSMD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref($default) })) }, // x[1..3] + (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), [Value::MatrixBool(Matrix::RowVector3(ix))]) => { + let len = input.borrow().len(); + Ok(Box::new(Access1DR3bR3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowDVector::from_element(len,$default)) })) + }, (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), [Value::MatrixIndex(Matrix::Vector2(ix))]) => { Ok(Box::new(Access1DV2R3{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector2::from_element($default)) })) }, diff --git a/src/syntax/src/value.rs b/src/syntax/src/value.rs index 75f9320..231895c 100644 --- a/src/syntax/src/value.rs +++ b/src/syntax/src/value.rs @@ -284,6 +284,7 @@ impl Value { Value::MatrixIndex(v) => Some(v.as_vec()), Value::MatrixI64(v) => Some(v.as_vec().iter().map(|x| *x as usize).collect::>()), Value::MutableReference(x) => x.borrow().as_vecusize(), + Value::MatrixBool(v) => None, _ => todo!(), } } @@ -297,7 +298,14 @@ impl Value { let out = Value::MatrixIndex(usize::to_matrix(x, shape[0], shape[1])); Ok(out) }, - None => Err(MechError {tokens: vec![], msg: file!().to_string(), id: line!(), kind: MechErrorKind::UnhandledIndexKind}), + None => match self.as_vecbool() { + Some(x) => { + let shape = self.shape(); + let out = Value::MatrixBool(bool::to_matrix(x, shape[0], shape[1])); + Ok(out) + } + None => Err(MechError {tokens: vec![], msg: file!().to_string(), id: line!(), kind: MechErrorKind::UnhandledIndexKind}), + } } } } diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index e7cbff2..598044b 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -140,6 +140,8 @@ test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := test_interpreter!(interpret_slice_ix_ref, "x := [94 53 13]; y := [3 3]; x[y]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![13,13]))))); test_interpreter!(interpret_slice_ix_ref2, "x := [94 53 13]; y := [3; 3]; x[y]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![13,13]))))); test_interpreter!(interpret_slice_ix_ref3, "x := [94 53 13]; y := 3; x[y]", Value::I64(new_ref(13))); +test_interpreter!(interpret_slice_logical_ix, "x := [94 53 13]; ix := [false true true]; x[ix]", Value::MatrixI64(Matrix::RowDVector(new_ref(RowDVector::from_vec(vec![53,13]))))); + test_interpreter!(interpret_set_empty,"{_}", Value::Set(MechSet::from_vec(vec![]))); test_interpreter!(interpret_set,"{1,2,3}", Value::Set(MechSet::from_vec(vec![Value::I64(new_ref(1)),Value::I64(new_ref(2)),Value::I64(new_ref(3))]))); From 4de1233abde72b54cd5ea08c21e85b6031631a5a Mon Sep 17 00:00:00 2001 From: cmontella Date: Fri, 2 Aug 2024 01:09:52 -0400 Subject: [PATCH 09/14] Implement the more access functions --- src/syntax/src/stdlib/matrix.rs | 93 +++++++++++++++------------------ src/syntax/tests/interpreter.rs | 10 ++-- 2 files changed, 48 insertions(+), 55 deletions(-) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index e3b43bd..a066180 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -318,65 +318,58 @@ macro_rules! impl_access_fxn { fn to_string(&self) -> String { format!("{:?}", self) } }};} +macro_rules! impl_access_fxn_shape { + ($name:ident, $ix_type:ty, $out_type:ty, $fxn:ident) => { + paste!{ + impl_access_fxn!([<$name V2>], Vector2, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name V3>], Vector3, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name V4>], Vector4, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name R2>], RowVector2, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name R3>], RowVector3, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name R4>], RowVector4, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M1>], Matrix1, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M2>], Matrix2, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M3>], Matrix3, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M4>], Matrix4, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M2x3>], Matrix2x3, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name M3x2>], Matrix3x2, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name MD>], DMatrix, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name RD>], RowDVector, $ix_type, $out_type, $fxn); + impl_access_fxn!([<$name VD>], DVector, $ix_type, $out_type, $fxn); + } + };} + // x[1] -impl_access_fxn!(Access1DSR2, RowVector2, usize, T, access_1d); -impl_access_fxn!(Access1DSR3, RowVector3, usize, T, access_1d); -impl_access_fxn!(Access1DSR4, RowVector4, usize, T, access_1d); -impl_access_fxn!(Access1DSM2, Matrix2, usize, T, access_1d); -impl_access_fxn!(Access1DSM3, Matrix3, usize, T, access_1d); -impl_access_fxn!(Access1DSM2x3, Matrix2x3, usize, T, access_1d); -impl_access_fxn!(Access1DSM3x2, Matrix3x2, usize, T, access_1d); -impl_access_fxn!(Access1DSMD, DMatrix, usize, T, access_1d); -impl_access_fxn!(Access1DSRD, RowDVector, usize, T, access_1d); -impl_access_fxn!(Access1DSVD, DVector, usize, T, access_1d); +impl_access_fxn_shape!(Access1DS, usize, T, access_1d); // x[1,2] -impl_access_fxn!(Access2DSR2, RowVector2, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSR3, RowVector3, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSR4, RowVector4, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSM2, Matrix2, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSM3, Matrix3, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSM2x3, Matrix2x3, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSM3x2, Matrix3x2, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSMD, DMatrix, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSRD, RowDVector, (usize,usize), T, access_2d); -impl_access_fxn!(Access2DSVD, DVector, (usize,usize), T, access_2d); +impl_access_fxn_shape!(Access2DS, (usize,usize), T, access_2d); // x[1..3] -impl_access_fxn!(Access1DV2R3, RowVector3, Vector2, Vector2, access_1d_slice2); -impl_access_fxn!(Access1DR2R3, RowVector3, RowVector2, RowVector2, access_1d_slice2); -impl_access_fxn!(Access1DR2RD, RowDVector, RowVector2, RowVector2, access_1d_slice2); -impl_access_fxn!(Access1DR3RD, RowDVector, RowVector3, RowVector3, access_1d_slice3); -impl_access_fxn!(Access1DR3bR3, RowVector3, RowVector3, RowDVector, access_1d_slice_bool); +impl_access_fxn_shape!(Access1DV2, Vector2, Vector2, access_1d_slice2); +impl_access_fxn_shape!(Access1DV3, Vector3, Vector3, access_1d_slice3); +impl_access_fxn_shape!(Access1DR2, RowVector2, RowVector2, access_1d_slice2); +impl_access_fxn_shape!(Access1DR3, RowVector3, RowVector3, access_1d_slice3); + +impl_access_fxn_shape!(Access1DR3b, RowVector3, RowDVector, access_1d_slice_bool); // x[1..3,1..3] -impl_access_fxn!(Access2DR2M3, Matrix3, (RowVector2,RowVector2), Matrix2, access_2d_slice2); -impl_access_fxn!(Access2DR2DM, DMatrix, (RowVector2,RowVector2), Matrix2, access_2d_slice2); +impl_access_fxn_shape!(Access2DR2, (RowVector2,RowVector2), Matrix2, access_2d_slice2); // x[:] -impl_access_fxn!(Access1DAM3x2, Matrix3x2, Value, DVector, access_1d_all); -impl_access_fxn!(Access1DAM2, Matrix2, Value, Vector4, access_1d_all); -impl_access_fxn!(Access1DAM3, Matrix3, Value, DVector, access_1d_all); -impl_access_fxn!(Access1DAMD, DMatrix, Value, DVector, access_1d_all); +impl_access_fxn_shape!(Access1DA, Value, DVector, access_1d_all); // x[:,1] -impl_access_fxn!(Access2DASM2, Matrix2, usize, Vector2, access_col); -impl_access_fxn!(Access2DASM3, Matrix3, usize, Vector3, access_col); -impl_access_fxn!(Access2DASMD, DMatrix, usize, DVector, access_col); +impl_access_fxn_shape!(Access2DAS, usize, DVector, access_col); // x[1,:] -impl_access_fxn!(Access2DSAM2, Matrix2, usize, RowVector2, access_row); -impl_access_fxn!(Access2DSAM3, Matrix3, usize, RowVector3, access_row); -impl_access_fxn!(Access2DSAMD, DMatrix, usize, RowDVector, access_row); +impl_access_fxn_shape!(Access2DSA, usize, RowDVector, access_row); // x[1..3,:] -impl_access_fxn!(Access2DR2AMD, DMatrix, RowVector2, DMatrix, access_2d_slice2_all); -impl_access_fxn!(Access2DR2AM3, Matrix3, RowVector2, Matrix2x3, access_2d_slice2_all); - +impl_access_fxn_shape!(Access2DR2A, RowVector2, DMatrix, access_2d_slice2_all); // x[:,1..3] -impl_access_fxn!(Access2DAR2MD, DMatrix, RowVector2, DMatrix, access_2d_all_slice2); -impl_access_fxn!(Access2DAR2M3, Matrix3, RowVector2, Matrix3x2, access_2d_all_slice2); +impl_access_fxn_shape!(Access2DAR2, RowVector2, DMatrix, access_2d_all_slice2); // x.x,y,z @@ -454,7 +447,7 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access2DR2M3{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::MatrixIndex(Matrix::RowVector2(ix1)), Value::MatrixIndex(Matrix::RowVector2(ix2))]) => { - Ok(Box::new(Access2DR2DM{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) + Ok(Box::new(Access2DR2MD{source: input.clone(), ixes: new_ref((ix1.borrow().clone(),ix2.borrow().clone())), out: new_ref(Matrix2::from_element($default)) })) }, // x[:] (Value::$matrix_kind(Matrix::<$target_type>::Matrix3x2(input)), [Value::IndexAll]) => { @@ -464,7 +457,7 @@ macro_rules! generate_access_match_arms { Ok(Box::new(Access1DAM3{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(9,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::IndexAll]) => { - Ok(Box::new(Access1DAM2{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(Vector4::from_element($default)) })) + Ok(Box::new(Access1DAM2{source: input.clone(), ixes: new_ref(Value::IndexAll), out: new_ref(DVector::from_element(4,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::IndexAll]) => { let len = input.borrow().len(); @@ -472,10 +465,10 @@ macro_rules! generate_access_match_arms { }, // x[:,2] (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::IndexAll,Value::Index(ix)]) => { - Ok(Box::new(Access2DASM2{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector2::from_element($default)) })) + Ok(Box::new(Access2DASM2{source: input.clone(), ixes: ix.clone(), out: new_ref(DVector::from_element(2,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll,Value::Index(ix)]) => { - Ok(Box::new(Access2DASM3{source: input.clone(), ixes: ix.clone(), out: new_ref(Vector3::from_element($default)) })) + Ok(Box::new(Access2DASM3{source: input.clone(), ixes: ix.clone(), out: new_ref(DVector::from_element(3,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::IndexAll,Value::Index(ix)]) => { let len = input.borrow().nrows(); @@ -483,10 +476,10 @@ macro_rules! generate_access_match_arms { }, // x[2,:] (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::Index(ix),Value::IndexAll]) => { - Ok(Box::new(Access2DSAM2{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector2::from_element($default)) })) + Ok(Box::new(Access2DSAM2{source: input.clone(), ixes: ix.clone(), out: new_ref(RowDVector::from_element(2,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::Index(ix),Value::IndexAll]) => { - Ok(Box::new(Access2DSAM3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowVector3::from_element($default)) })) + Ok(Box::new(Access2DSAM3{source: input.clone(), ixes: ix.clone(), out: new_ref(RowDVector::from_element(3,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::Index(ix),Value::IndexAll]) => { let len = input.borrow().ncols(); @@ -495,7 +488,7 @@ macro_rules! generate_access_match_arms { // x[1..3,:] (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::MatrixIndex(Matrix::RowVector2(ix)), Value::IndexAll]) => { let cols = input.borrow().ncols(); - Ok(Box::new(Access2DR2AM3{source: input.clone(), ixes: ix.clone(), out: new_ref(Matrix2x3::from_element($default)) })) + Ok(Box::new(Access2DR2AM3{source: input.clone(), ixes: ix.clone(), out: new_ref(DMatrix::from_element(2,3,$default)) })) }, (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), [Value::MatrixIndex(Matrix::RowVector2(ix)), Value::IndexAll]) => { let cols = input.borrow().ncols(); @@ -508,7 +501,7 @@ macro_rules! generate_access_match_arms { }, // x[:,1..3] (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), [Value::IndexAll, Value::MatrixIndex(Matrix::RowVector2(ix))]) => { - Ok(Box::new(Access2DAR2M3{source: input.clone(), ixes: ix.clone(), out: new_ref(Matrix3x2::from_element($default)) })) + Ok(Box::new(Access2DAR2M3{source: input.clone(), ixes: ix.clone(), out: new_ref(DMatrix::from_element(3,2,$default)) })) }, )+ )+ diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 598044b..83528ee 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -130,12 +130,12 @@ test_interpreter!(interpret_slice_f64, "a := [1.0,2.0,3.0]; a[2]", Value::F64(ne test_interpreter!(interpret_slice_2d_f64, "a := [1,2;3,4]; a[2,1]", Value::I64(new_ref(3))); test_interpreter!(interpret_slice_range, "x := 4..10; x[1..=3]", Value::MatrixI64(Matrix::RowVector3(new_ref(RowVector3::from_vec(vec![4,5,6]))))); test_interpreter!(interpret_slice_range_2d, "x := [1 2 3; 4 5 6; 7 8 9]; x[2..=3, 2..=3]", Value::MatrixI64(Matrix::Matrix2(new_ref(Matrix2::from_vec(vec![5,8,6,9]))))); -test_interpreter!(interpret_slice_all, "x := [1 2; 4 5]; x[:]", Value::MatrixI64(Matrix::Vector4(new_ref(Vector4::from_vec(vec![1,4,2,5]))))); -test_interpreter!(interpret_slice_all_2d, "x := [1 2; 4 5]; x[:,2]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![2,5]))))); -test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![4,5]))))); +test_interpreter!(interpret_slice_all, "x := [1 2; 4 5]; x[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,2,5]))))); +test_interpreter!(interpret_slice_all_2d, "x := [1 2; 4 5]; x[:,2]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![2,5]))))); +test_interpreter!(interpret_slice_all_2d_row, "x := [1 2; 4 5]; x[2,:]", Value::MatrixI64(Matrix::RowDVector(new_ref(RowDVector::from_vec(vec![4,5]))))); test_interpreter!(interpret_slice_all_range, "x := [1 2 3 4; 5 6 7 8]; x[:,1..=2]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,2,vec![1,5,2,6]))))); -test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,4,2,5,3,6]))))); -test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::Matrix2x3(new_ref(Matrix2x3::from_vec(vec![1,1,2,2,3,3]))))); +test_interpreter!(interpret_slice_range_all, "x := [1 2 3; 4 5 6; 7 8 9]; x[1..=2,:]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,3,vec![1,4,2,5,3,6]))))); +test_interpreter!(interpret_slice_range_dupe, "x := [1 2 3; 4 5 6; 7 8 9]; x[[1 1],:]", Value::MatrixI64(Matrix::DMatrix(new_ref(DMatrix::from_vec(2,3,vec![1,1,2,2,3,3]))))); test_interpreter!(interpret_slice_all_reshape, "x := [1 2 3; 4 5 6; 7 8 9]; y := x[:,[1,1]]; y[:]", Value::MatrixI64(Matrix::DVector(new_ref(DVector::from_vec(vec![1,4,7,1,4,7]))))); test_interpreter!(interpret_slice_ix_ref, "x := [94 53 13]; y := [3 3]; x[y]", Value::MatrixI64(Matrix::RowVector2(new_ref(RowVector2::from_vec(vec![13,13]))))); test_interpreter!(interpret_slice_ix_ref2, "x := [94 53 13]; y := [3; 3]; x[y]", Value::MatrixI64(Matrix::Vector2(new_ref(Vector2::from_vec(vec![13,13]))))); From 0be9c79549da94645e41f07c1c130f90035bf8ab Mon Sep 17 00:00:00 2001 From: cmontella Date: Sat, 3 Aug 2024 01:06:25 -0400 Subject: [PATCH 10/14] impl some more functions --- src/syntax/src/stdlib/matrix.rs | 42 +++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index a066180..ce09064 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -236,6 +236,28 @@ macro_rules! access_1d_slice_bool { } }};} +macro_rules! access_1d_slice_bool_v { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + let mut j = 0; + let out_len = (*$out).len(); + for i in 0..(*$ix).len() { + if (*$ix)[i] == true { + j += 1; + } + } + if j != out_len { + (*$out).resize_vertically_mut(j,(*$out)[0]); + } + j = 0; + for i in 0..(*$source).len() { + if (*$ix)[i] == true { + (*$out)[j] = (*$source).index(i).clone(); + j += 1; + } + } + }};} + macro_rules! access_2d_slice2 { ($source:expr, $ix:expr, $out:expr) => { unsafe { @@ -257,6 +279,20 @@ macro_rules! access_2d_slice2_all { out_ix += 1; }}};} +macro_rules! access_2d_slice3_all { + ($source:expr, $ix:expr, $out:expr) => { + unsafe { + let n_cols = (*$out).ncols(); + let mut out_ix = 0; + for i in 0..n_cols { + (*$out)[out_ix] = (*$source).index(((*$ix)[0] - 1, i)).clone(); + out_ix += 1; + (*$out)[out_ix] = (*$source).index(((*$ix)[1] - 1, i)).clone(); + out_ix += 1; + (*$out)[out_ix] = (*$source).index(((*$ix)[2] - 1, i)).clone(); + out_ix += 1; + }}};} + macro_rules! access_2d_all_slice2 { ($source:expr, $ix:expr, $out:expr) => { unsafe { @@ -351,7 +387,12 @@ impl_access_fxn_shape!(Access1DV3, Vector3, Vector3, access_1d_slice3) impl_access_fxn_shape!(Access1DR2, RowVector2, RowVector2, access_1d_slice2); impl_access_fxn_shape!(Access1DR3, RowVector3, RowVector3, access_1d_slice3); +impl_access_fxn_shape!(Access1DR2b, RowVector2, RowDVector, access_1d_slice_bool); impl_access_fxn_shape!(Access1DR3b, RowVector3, RowDVector, access_1d_slice_bool); +impl_access_fxn_shape!(Access1DR4b, RowVector4, RowDVector, access_1d_slice_bool); +impl_access_fxn_shape!(Access1DV2b, Vector2, DVector, access_1d_slice_bool_v); +impl_access_fxn_shape!(Access1DV3b, Vector3, DVector, access_1d_slice_bool_v); +impl_access_fxn_shape!(Access1DV4b, Vector4, DVector, access_1d_slice_bool_v); // x[1..3,1..3] impl_access_fxn_shape!(Access2DR2, (RowVector2,RowVector2), Matrix2, access_2d_slice2); @@ -367,6 +408,7 @@ impl_access_fxn_shape!(Access2DSA, usize, RowDVector, access_row); // x[1..3,:] impl_access_fxn_shape!(Access2DR2A, RowVector2, DMatrix, access_2d_slice2_all); +impl_access_fxn_shape!(Access2DR3A, RowVector3, DMatrix, access_2d_slice3_all); // x[:,1..3] impl_access_fxn_shape!(Access2DAR2, RowVector2, DMatrix, access_2d_all_slice2); From 02a00460d90b2ba65269993f93c599b160c05f6d Mon Sep 17 00:00:00 2001 From: cmontella Date: Sun, 4 Aug 2024 01:53:40 -0400 Subject: [PATCH 11/14] making progress on refactoring matrix access --- src/syntax/src/interpreter.rs | 21 ++++++++++++++++++++- src/syntax/src/stdlib/matrix.rs | 9 +++++++++ src/syntax/tests/interpreter.rs | 1 + 3 files changed, 30 insertions(+), 1 deletion(-) diff --git a/src/syntax/src/interpreter.rs b/src/syntax/src/interpreter.rs index c55b086..674b4ea 100644 --- a/src/syntax/src/interpreter.rs +++ b/src/syntax/src/interpreter.rs @@ -359,12 +359,31 @@ fn subscript(sbscrpt: &Subscript, val: &Value, plan: Plan, symbols: SymbolTableR result.as_index() }, Subscript::Bracket(subs) => { + let mut fxn_input = vec![val.clone()]; + match &subs[..] { + [Subscript::Formula(ix)] => { + let result = factor(&ix, plan.clone(), symbols.clone(), functions.clone())?; + fxn_input.push(result); + let new_fxn = MatrixAccess{}.compile(&fxn_input)?; + }, + [Subscript::Range(ix)] => todo!(), + [Subscript::All] => todo!(), + [Subscript::All,Subscript::All] => todo!(), + [Subscript::Formula(ix1),Subscript::Formula(ix2)] => todo!(), + [Subscript::Range(ix1),Subscript::Range(ix2)] => todo!(), + [Subscript::All,Subscript::Formula(ix2)] => todo!(), + [Subscript::Formula(ix1),Subscript::All] => todo!(), + [Subscript::Range(ix1),Subscript::Formula(ix2)] => todo!(), + [Subscript::Formula(ix1),Subscript::Range(ix2)] => todo!(), + [Subscript::All,Subscript::Range(ix2)] => todo!(), + [Subscript::Range(ix1),Subscript::All] => todo!(), + _ => unreachable!() + } let mut resolved_subs = vec![]; for s in subs { let result = subscript(&s, val, plan.clone(), symbols.clone(), functions.clone())?; resolved_subs.push(result); } - let mut fxn_input = vec![val.clone()]; fxn_input.append(&mut resolved_subs); let new_fxn = MatrixAccess{}.compile(&fxn_input)?; new_fxn.solve(); diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index ce09064..46ddfb4 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -430,6 +430,15 @@ macro_rules! generate_access_match_arms { (Value::$matrix_kind(Matrix::<$target_type>::RowVector2(input)), [Value::Index(ix)]) => { Ok(Box::new(Access1DSR2{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector4(input)), [Value::Index(ix)]) => { + Ok(Box::new(Access1DSV4{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector3(input)), [Value::Index(ix)]) => { + Ok(Box::new(Access1DSV3{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector2(input)), [Value::Index(ix)]) => { + Ok(Box::new(Access1DSV2{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) + }, (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), [Value::Index(ix)]) => { Ok(Box::new(Access1DSM2{source: input.clone(), ixes: ix.clone(), out: new_ref($default) })) }, diff --git a/src/syntax/tests/interpreter.rs b/src/syntax/tests/interpreter.rs index 83528ee..8791ed1 100644 --- a/src/syntax/tests/interpreter.rs +++ b/src/syntax/tests/interpreter.rs @@ -125,6 +125,7 @@ test_interpreter!(interpret_tuple, "(1,true)", Value::Tuple(MechTuple::from_vec( test_interpreter!(interpret_tuple_nested, r#"(1,("Hello",false))"#, Value::Tuple(MechTuple::from_vec(vec![Value::I64(new_ref(1)), Value::Tuple(MechTuple::from_vec(vec![Value::String("Hello".to_string()), Value::Bool(new_ref(false))]))]))); test_interpreter!(interpret_slice, "a := [1,2,3]; a[2]", Value::I64(new_ref(2))); +test_interpreter!(interpret_slice_v, "a := [1,2,3]'; a[2]", Value::I64(new_ref(2))); test_interpreter!(interpret_slice_2d, "a := [1,2;3,4]; a[1,2]", Value::I64(new_ref(2))); test_interpreter!(interpret_slice_f64, "a := [1.0,2.0,3.0]; a[2]", Value::F64(new_ref(F64::new(2.0)))); test_interpreter!(interpret_slice_2d_f64, "a := [1,2;3,4]; a[2,1]", Value::I64(new_ref(3))); From 70dec7ad4b598ca9ac30d3e119df9bcff68f3d0b Mon Sep 17 00:00:00 2001 From: cmontella Date: Mon, 5 Aug 2024 19:23:19 -0400 Subject: [PATCH 12/14] Fix tests --- src/syntax/src/interpreter.rs | 35 +++++++----- src/syntax/src/stdlib/matrix.rs | 99 +++++++++++++++++++++++++++++++++ 2 files changed, 119 insertions(+), 15 deletions(-) diff --git a/src/syntax/src/interpreter.rs b/src/syntax/src/interpreter.rs index 674b4ea..9a5fc98 100644 --- a/src/syntax/src/interpreter.rs +++ b/src/syntax/src/interpreter.rs @@ -360,25 +360,30 @@ fn subscript(sbscrpt: &Subscript, val: &Value, plan: Plan, symbols: SymbolTableR }, Subscript::Bracket(subs) => { let mut fxn_input = vec![val.clone()]; - match &subs[..] { + /*match &subs[..] { [Subscript::Formula(ix)] => { let result = factor(&ix, plan.clone(), symbols.clone(), functions.clone())?; - fxn_input.push(result); - let new_fxn = MatrixAccess{}.compile(&fxn_input)?; + fxn_input.push(result.as_index()?); + let new_fxn = MatrixAccessFormula{}.compile(&fxn_input)?; + new_fxn.solve(); + let res = new_fxn.out(); + let mut plan_brrw = plan.borrow_mut(); + plan_brrw.push(new_fxn); + return Ok(res); }, - [Subscript::Range(ix)] => todo!(), - [Subscript::All] => todo!(), - [Subscript::All,Subscript::All] => todo!(), - [Subscript::Formula(ix1),Subscript::Formula(ix2)] => todo!(), - [Subscript::Range(ix1),Subscript::Range(ix2)] => todo!(), - [Subscript::All,Subscript::Formula(ix2)] => todo!(), - [Subscript::Formula(ix1),Subscript::All] => todo!(), - [Subscript::Range(ix1),Subscript::Formula(ix2)] => todo!(), - [Subscript::Formula(ix1),Subscript::Range(ix2)] => todo!(), - [Subscript::All,Subscript::Range(ix2)] => todo!(), - [Subscript::Range(ix1),Subscript::All] => todo!(), + [Subscript::Range(ix)] => (), + [Subscript::All] => (), + [Subscript::All,Subscript::All] => (), + [Subscript::Formula(ix1),Subscript::Formula(ix2)] => (), + [Subscript::Range(ix1),Subscript::Range(ix2)] => (), + [Subscript::All,Subscript::Formula(ix2)] => (), + [Subscript::Formula(ix1),Subscript::All] => (), + [Subscript::Range(ix1),Subscript::Formula(ix2)] => (), + [Subscript::Formula(ix1),Subscript::Range(ix2)] => (), + [Subscript::All,Subscript::Range(ix2)] => (), + [Subscript::Range(ix1),Subscript::All] => (), _ => unreachable!() - } + }*/ let mut resolved_subs = vec![]; for s in subs { let result = subscript(&s, val, plan.clone(), symbols.clone(), functions.clone())?; diff --git a/src/syntax/src/stdlib/matrix.rs b/src/syntax/src/stdlib/matrix.rs index 46ddfb4..6a10af9 100644 --- a/src/syntax/src/stdlib/matrix.rs +++ b/src/syntax/src/stdlib/matrix.rs @@ -598,4 +598,103 @@ impl NativeFunctionCompiler for MatrixAccess { } } } +} + +macro_rules! generate_access_formula_match_arms { + ($fxn_name:ident, $ix:tt, $ixes:expr, $arg:expr, $($input_type:ident => $($matrix_kind:ident, $target_type:ident, $default:expr),+);+ $(;)?) => { + paste!{ + match $arg { + $( + $( + // x[1] + (Value::$matrix_kind(Matrix::<$target_type>::RowVector4(input)), $ix) => { + Ok(Box::new([<$fxn_name R4>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::RowVector3(input)), $ix) => { + Ok(Box::new([<$fxn_name R3>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::RowVector2(input)), $ix) => { + Ok(Box::new([<$fxn_name R2>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector4(input)), $ix) => { + Ok(Box::new([<$fxn_name V4>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector3(input)), $ix) => { + Ok(Box::new([<$fxn_name V3>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Vector2(input)), $ix) => { + Ok(Box::new([<$fxn_name V2>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2(input)), $ix) => { + Ok(Box::new([<$fxn_name M2>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3(input)), $ix) => { + Ok(Box::new([<$fxn_name M3>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix4(input)), $ix) => { + Ok(Box::new([<$fxn_name M4>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix2x3(input)), $ix) => { + Ok(Box::new([<$fxn_name M2x3>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::Matrix3x2(input)), $ix) => { + Ok(Box::new([<$fxn_name M3x2>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DMatrix(input)), $ix) => { + Ok(Box::new([<$fxn_name MD>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::RowDVector(input)), $ix) => { + Ok(Box::new([<$fxn_name RD>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + (Value::$matrix_kind(Matrix::<$target_type>::DVector(input)), $ix) => { + Ok(Box::new([<$fxn_name VD>]{source: input.clone(), ixes: $ixes, out: new_ref($default) })) + }, + + )+ + )+ + x => Err(MechError { tokens: vec![], msg: format!("{:?}",x), id: 314, kind: MechErrorKind::UnhandledFunctionArgumentKind }), + } + } + } +} + +fn generate_access_formula_fxn(lhs_value: Value, ixes: Vec) -> Result, MechError> { + generate_access_formula_match_arms!( + Access1DS, + [Value::Index(ix)],ix.clone(), + (lhs_value, ixes.as_slice()), + Bool => MatrixBool, bool, false; + I8 => MatrixI8, i8, i8::zero(); + I16 => MatrixI16, i16, i16::zero(); + I32 => MatrixI32, i32, i32::zero(); + I64 => MatrixI64, i64, i64::zero(); + I128 => MatrixI128, i128, i128::zero(); + U8 => MatrixU8, u8, u8::zero(); + U16 => MatrixU16, u16, u16::zero(); + U32 => MatrixU32, u32, u32::zero(); + U64 => MatrixU64, u64, u64::zero(); + U128 => MatrixU128, u128, u128::zero(); + F32 => MatrixF32, F32, F32::zero(); + F64 => MatrixF64, F64, F64::zero(); + ) +} + +pub struct MatrixAccessFormula {} +impl NativeFunctionCompiler for MatrixAccessFormula { + fn compile(&self, arguments: &Vec) -> MResult> { + if arguments.len() <= 1 { + return Err(MechError {tokens: vec![], msg: file!().to_string(), id: line!(), kind: MechErrorKind::IncorrectNumberOfArguments}); + } + let ixes = arguments.clone().split_off(1); + let mat = arguments[0].clone(); + match generate_access_formula_fxn(mat.clone(), ixes.clone()) { + Ok(fxn) => Ok(fxn), + Err(_) => { + match (mat,ixes) { + (Value::MutableReference(lhs),rhs_value) => { generate_access_formula_fxn(lhs.borrow().clone(), rhs_value.clone()) } + x => Err(MechError { tokens: vec![], msg: file!().to_string(), id: line!(), kind: MechErrorKind::UnhandledFunctionArgumentKind }), + } + } + } + } } \ No newline at end of file From a08e688540322d089f71c287a9c71081c770867c Mon Sep 17 00:00:00 2001 From: cmontella Date: Mon, 5 Aug 2024 19:42:00 -0400 Subject: [PATCH 13/14] Upgrade version --- src/core/Cargo.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/Cargo.toml b/src/core/Cargo.toml index 2d26a23..36a1517 100644 --- a/src/core/Cargo.toml +++ b/src/core/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mech-core" -version = "0.2.4" +version = "0.2.5" authors = ["Corey Montella "] description = "The Mech language runtime." documentation = "http://docs.mech-lang.org" From e6d14f44da0bd2ca754d2614a2008143e747bb39 Mon Sep 17 00:00:00 2001 From: cmontella Date: Mon, 5 Aug 2024 19:42:48 -0400 Subject: [PATCH 14/14] Upgrade version --- Cargo.toml | 6 +++--- src/bin/mech.rs | 2 +- src/syntax/Cargo.toml | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 0e109ea..b3b1ada 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mech" -version = "0.2.4" +version = "0.2.5" authors = ["Corey Montella "] description = "Toolchain for the Mech programming language." documentation = "https://mech-lang.org/docs" @@ -18,8 +18,8 @@ gitlab = { repository = "mech-lang/mech", branch = "main" } maintenance = { status = "actively-developed" } [dependencies] -mech-core = "0.2.4" -mech-syntax = "0.2.4" +mech-core = "0.2.5" +mech-syntax = "0.2.5" #mech-program = "0.2.2" #mech-utilities = "0.2.2" diff --git a/src/bin/mech.rs b/src/bin/mech.rs index 3385694..612823f 100644 --- a/src/bin/mech.rs +++ b/src/bin/mech.rs @@ -25,7 +25,7 @@ use serde_json; fn main() -> Result<(), MechError> { - let version = "0.2.4"; + let version = "0.2.5"; let text_logo = r#" ┌─────────┐ ┌──────┐ ┌─┐ ┌──┐ ┌─┐ ┌─┐ └───┐ ┌───┘ └──────┘ │ │ └┐ │ │ │ │ │ diff --git a/src/syntax/Cargo.toml b/src/syntax/Cargo.toml index e367266..252c69f 100644 --- a/src/syntax/Cargo.toml +++ b/src/syntax/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "mech-syntax" -version = "0.2.4" +version = "0.2.5" authors = ["Corey Montella "] description = "A toolchain for compiling textual syntax into Mech blocks." documentation = "http://docs.mech-lang.org" @@ -21,7 +21,7 @@ default = [] no-std = ["mech-core/no-std", "rlibc"] [dependencies] -mech-core = "0.2.4" +mech-core = "0.2.5" hashbrown = "0.14.5" lazy_static = "1.4.0"