diff --git a/boa_engine/src/builtins/array/mod.rs b/boa_engine/src/builtins/array/mod.rs index 9a2a094130..8c3f386707 100644 --- a/boa_engine/src/builtins/array/mod.rs +++ b/boa_engine/src/builtins/array/mod.rs @@ -1157,6 +1157,22 @@ impl Array { // b. Return undefined. return Ok(JsValue::undefined()); } + + // Small optimization for arrays using dense properties + // TODO: this optimization could be generalized to many other objects with + // slot-based dense property maps. + if o.is_array() { + let mut o_borrow = o.borrow_mut(); + if let Some(dense) = o_borrow.properties_mut().dense_indexed_properties_mut() { + if len <= dense.len() as u64 { + let v = dense.remove(0); + drop(o_borrow); + Self::set_length(&o, len - 1, context)?; + return Ok(v); + } + } + } + // 4. Let first be ? Get(O, "0"). let first = o.get(0, context)?; // 5. Let k be 1. diff --git a/boa_engine/src/object/property_map.rs b/boa_engine/src/object/property_map.rs index 8320fe1d88..a7046fde8f 100644 --- a/boa_engine/src/object/property_map.rs +++ b/boa_engine/src/object/property_map.rs @@ -55,7 +55,7 @@ enum IndexedProperties { /// are not data descriptors with with a value field, writable field set to `true`, configurable field set to `true`, enumerable field set to `true`. /// /// This method uses more space, since we also have to store the property descriptors, not just the value. - /// It is also slower because we need to to a hash lookup. + /// It is also slower because we need to do a hash lookup. Sparse(Box>), } @@ -150,7 +150,7 @@ impl IndexedProperties { replaced } - /// Inserts a property descriptor with the specified key. + /// Removes a property descriptor with the specified key. fn remove(&mut self, key: u32) -> bool { let vec = match self { Self::Sparse(map) => {