From 4ac0078cdbea3fdb395c62077290e6368f13533d Mon Sep 17 00:00:00 2001 From: XX Date: Sun, 8 Apr 2018 16:25:56 +0300 Subject: Fix initialy set arr path --- src/path/mod.rs | 171 +++++++++++++++++++++++++++++++++++------------------ src/path/parser.rs | 9 +++ 2 files changed, 124 insertions(+), 56 deletions(-) (limited to 'src/path') diff --git a/src/path/mod.rs b/src/path/mod.rs index 258c4c4..f042992 100644 --- a/src/path/mod.rs +++ b/src/path/mod.rs @@ -58,77 +58,138 @@ impl Expression { } } - Expression::Subscript(expr, index) => match expr.get(root) { - Some(value) => match value.kind { - ValueKind::Array(ref array) => { - let index = sindex_to_uindex(index, array.len()); - - if index >= array.len() { - None - } else { - Some(&array[index]) + Expression::Subscript(expr, index) => { + match expr.get(root) { + Some(value) => match value.kind { + ValueKind::Array(ref array) => { + let index = sindex_to_uindex(index, array.len()); + + if index >= array.len() { + None + } else { + Some(&array[index]) + } } - } - _ => None, - }, + _ => None, + }, - _ => None, + _ => None, + } }, } } pub fn get_mut<'a>(&self, root: &'a mut Value) -> Option<&'a mut Value> { match *self { - Expression::Identifier(ref id) => match root.kind { - ValueKind::Table(ref mut map) => Some( - map.entry(id.clone()) - .or_insert_with(|| Value::new(None, ValueKind::Nil)), - ), + Expression::Identifier(ref id) => { + match root.kind { + ValueKind::Table(ref mut map) => map.get_mut(id), - _ => None, + _ => None, + } }, - Expression::Child(ref expr, ref key) => match expr.get_mut(root) { - Some(value) => match value.kind { + Expression::Child(ref expr, ref key) => { + match expr.get_mut(root) { + Some(value) => { + match value.kind { + ValueKind::Table(ref mut map) => map.get_mut(key), + + _ => None + } + }, + + _ => None, + } + }, + + Expression::Subscript(ref expr, index) => { + match expr.get_mut(root) { + Some(value) => match value.kind { + ValueKind::Array(ref mut array) => { + let index = sindex_to_uindex(index, array.len()); + + if index >= array.len() { + None + } else { + Some(&mut array[index]) + } + } + + _ => None, + }, + + _ => None, + } + }, + } + } + + pub fn get_mut_forcibly<'a>(&self, root: &'a mut Value) -> Option<&'a mut Value> { + match *self { + Expression::Identifier(ref id) => { + match root.kind { ValueKind::Table(ref mut map) => Some( - map.entry(key.clone()) + map.entry(id.clone()) .or_insert_with(|| Value::new(None, ValueKind::Nil)), ), - _ => { - *value = HashMap::::new().into(); + _ => None, + } + }, - if let ValueKind::Table(ref mut map) = value.kind { - Some( - map.entry(key.clone()) - .or_insert_with(|| Value::new(None, ValueKind::Nil)), - ) - } else { - unreachable!(); + Expression::Child(ref expr, ref key) => { + match expr.get_mut_forcibly(root) { + Some(value) => match value.kind { + ValueKind::Table(ref mut map) => Some( + map.entry(key.clone()) + .or_insert_with(|| Value::new(None, ValueKind::Nil)), + ), + + _ => { + *value = HashMap::::new().into(); + + if let ValueKind::Table(ref mut map) = value.kind { + Some( + map.entry(key.clone()) + .or_insert_with(|| Value::new(None, ValueKind::Nil)), + ) + } else { + unreachable!(); + } } - } - }, + }, - _ => None, + _ => None, + } }, - Expression::Subscript(ref expr, index) => match expr.get_mut(root) { - Some(value) => match value.kind { - ValueKind::Array(ref mut array) => { - let index = sindex_to_uindex(index, array.len()); - - if index >= array.len() { - array.resize((index + 1) as usize, Value::new(None, ValueKind::Nil)); + Expression::Subscript(ref expr, index) => { + let mut do_again = false; + match expr.get_mut_forcibly(root) { + Some(value) => { + match value.kind { + ValueKind::Array(_) => (), + _ => *value = Vec::::new().into() } - Some(&mut array[index]) - } + match value.kind { + ValueKind::Array(ref mut array) => { + let index = sindex_to_uindex(index, array.len()); - _ => None, - }, + if index >= array.len() { + array.resize((index + 1) as usize, Value::new(None, ValueKind::Nil)); + } + + Some(&mut array[index]) + } - _ => None, + _ => None + } + }, + _ => None + } }, } } @@ -171,7 +232,7 @@ impl Expression { } Expression::Child(ref expr, ref key) => { - if let Some(parent) = expr.get_mut(root) { + if let Some(parent) = expr.get_mut_forcibly(root) { match parent.kind { ValueKind::Table(_) => { Expression::Identifier(key.clone()).set(parent, value); @@ -188,11 +249,15 @@ impl Expression { } Expression::Subscript(ref expr, index) => { - if let Some(parent) = expr.get_mut(root) { + if let Some(parent) = expr.get_mut_forcibly(root) { + match parent.kind { + ValueKind::Array(_) => (), + _ => *parent = Vec::::new().into() + } + match parent.kind { ValueKind::Array(ref mut array) => { let uindex = sindex_to_uindex(index, array.len()); - if uindex >= array.len() { array.resize( (uindex + 1) as usize, @@ -203,13 +268,7 @@ impl Expression { array[uindex] = value.clone(); } - _ => { - // Didn't find an array ... - // Add an array and do this again - *parent = Vec::::new().into(); - - Expression::Subscript(expr.clone(), index).set(parent, value); - } + _ => () } } } diff --git a/src/path/parser.rs b/src/path/parser.rs index 7629193..3ec433e 100644 --- a/src/path/parser.rs +++ b/src/path/parser.rs @@ -101,6 +101,15 @@ mod test { let expected = Child(Box::new(Identifier("abcd".into())), "efgh".into()); assert_eq!(parsed, expected); + + let parsed: Expression = from_str("abcd.efgh.ijkl").unwrap(); + let expected = Child(Box::new( + Child(Box::new( + Identifier("abcd".into()) + ), "efgh".into()) + ), "ijkl".into()); + + assert_eq!(parsed, expected); } #[test] -- cgit v1.2.3