Path: blob/main/cranelift/entity/src/boxed_slice.rs
1692 views
//! Boxed slices for `PrimaryMap`.12use crate::EntityRef;3use crate::iter::{Iter, IterMut};4use crate::keys::Keys;5use alloc::boxed::Box;6use core::marker::PhantomData;7use core::ops::{Index, IndexMut};8use core::slice;910/// A slice mapping `K -> V` allocating dense entity references.11///12/// The `BoxedSlice` data structure uses the dense index space to implement a map with a boxed13/// slice.14#[derive(Debug, Clone)]15pub struct BoxedSlice<K, V>16where17K: EntityRef,18{19elems: Box<[V]>,20unused: PhantomData<K>,21}2223impl<K, V> BoxedSlice<K, V>24where25K: EntityRef,26{27/// Create a new slice from a raw pointer. A safer way to create slices is28/// to use `PrimaryMap::into_boxed_slice()`.29///30/// # Safety31///32/// This relies on `raw` pointing to a valid slice of `V`s.33pub unsafe fn from_raw(raw: *mut [V]) -> Self {34Self {35elems: unsafe { Box::from_raw(raw) },36unused: PhantomData,37}38}3940/// Check if `k` is a valid key in the map.41pub fn is_valid(&self, k: K) -> bool {42k.index() < self.elems.len()43}4445/// Get the element at `k` if it exists.46pub fn get(&self, k: K) -> Option<&V> {47self.elems.get(k.index())48}4950/// Get the element at `k` if it exists, mutable version.51pub fn get_mut(&mut self, k: K) -> Option<&mut V> {52self.elems.get_mut(k.index())53}5455/// Is this map completely empty?56pub fn is_empty(&self) -> bool {57self.elems.is_empty()58}5960/// Get the total number of entity references created.61pub fn len(&self) -> usize {62self.elems.len()63}6465/// Iterate over all the keys in this map.66pub fn keys(&self) -> Keys<K> {67Keys::with_len(self.elems.len())68}6970/// Iterate over all the values in this map.71pub fn values(&self) -> slice::Iter<'_, V> {72self.elems.iter()73}7475/// Iterate over all the values in this map, mutable edition.76pub fn values_mut(&mut self) -> slice::IterMut<'_, V> {77self.elems.iter_mut()78}7980/// Iterate over all the keys and values in this map.81pub fn iter(&self) -> Iter<'_, K, V> {82Iter::new(self.elems.iter())83}8485/// Iterate over all the keys and values in this map, mutable edition.86pub fn iter_mut(&mut self) -> IterMut<'_, K, V> {87IterMut::new(self.elems.iter_mut())88}8990/// Returns the last element that was inserted in the map.91pub fn last(&self) -> Option<&V> {92self.elems.last()93}94}9596/// Immutable indexing into a `BoxedSlice`.97/// The indexed value must be in the map.98impl<K, V> Index<K> for BoxedSlice<K, V>99where100K: EntityRef,101{102type Output = V;103104fn index(&self, k: K) -> &V {105&self.elems[k.index()]106}107}108109/// Mutable indexing into a `BoxedSlice`.110impl<K, V> IndexMut<K> for BoxedSlice<K, V>111where112K: EntityRef,113{114fn index_mut(&mut self, k: K) -> &mut V {115&mut self.elems[k.index()]116}117}118119impl<'a, K, V> IntoIterator for &'a BoxedSlice<K, V>120where121K: EntityRef,122{123type Item = (K, &'a V);124type IntoIter = Iter<'a, K, V>;125126fn into_iter(self) -> Self::IntoIter {127Iter::new(self.elems.iter())128}129}130131impl<'a, K, V> IntoIterator for &'a mut BoxedSlice<K, V>132where133K: EntityRef,134{135type Item = (K, &'a mut V);136type IntoIter = IterMut<'a, K, V>;137138fn into_iter(self) -> Self::IntoIter {139IterMut::new(self.elems.iter_mut())140}141}142143#[cfg(test)]144mod tests {145use super::*;146use crate::primary::PrimaryMap;147use alloc::vec::Vec;148149// `EntityRef` impl for testing.150#[derive(Clone, Copy, Debug, PartialEq, Eq)]151struct E(u32);152153impl EntityRef for E {154fn new(i: usize) -> Self {155E(i as u32)156}157fn index(self) -> usize {158self.0 as usize159}160}161162#[test]163fn basic() {164let r0 = E(0);165let r1 = E(1);166let p = PrimaryMap::<E, isize>::new();167let m = p.into_boxed_slice();168169let v: Vec<E> = m.keys().collect();170assert_eq!(v, []);171172assert!(!m.is_valid(r0));173assert!(!m.is_valid(r1));174}175176#[test]177fn iter() {178let mut p: PrimaryMap<E, usize> = PrimaryMap::new();179p.push(12);180p.push(33);181let mut m = p.into_boxed_slice();182183let mut i = 0;184for (key, value) in &m {185assert_eq!(key.index(), i);186match i {1870 => assert_eq!(*value, 12),1881 => assert_eq!(*value, 33),189_ => panic!(),190}191i += 1;192}193i = 0;194for (key_mut, value_mut) in m.iter_mut() {195assert_eq!(key_mut.index(), i);196match i {1970 => assert_eq!(*value_mut, 12),1981 => assert_eq!(*value_mut, 33),199_ => panic!(),200}201i += 1;202}203}204205#[test]206fn iter_rev() {207let mut p: PrimaryMap<E, usize> = PrimaryMap::new();208p.push(12);209p.push(33);210let mut m = p.into_boxed_slice();211212let mut i = 2;213for (key, value) in m.iter().rev() {214i -= 1;215assert_eq!(key.index(), i);216match i {2170 => assert_eq!(*value, 12),2181 => assert_eq!(*value, 33),219_ => panic!(),220}221}222223i = 2;224for (key, value) in m.iter_mut().rev() {225i -= 1;226assert_eq!(key.index(), i);227match i {2280 => assert_eq!(*value, 12),2291 => assert_eq!(*value, 33),230_ => panic!(),231}232}233}234#[test]235fn keys() {236let mut p: PrimaryMap<E, usize> = PrimaryMap::new();237p.push(12);238p.push(33);239let m = p.into_boxed_slice();240241let mut i = 0;242for key in m.keys() {243assert_eq!(key.index(), i);244i += 1;245}246}247248#[test]249fn keys_rev() {250let mut p: PrimaryMap<E, usize> = PrimaryMap::new();251p.push(12);252p.push(33);253let m = p.into_boxed_slice();254255let mut i = 2;256for key in m.keys().rev() {257i -= 1;258assert_eq!(key.index(), i);259}260}261262#[test]263fn values() {264let mut p: PrimaryMap<E, usize> = PrimaryMap::new();265p.push(12);266p.push(33);267let mut m = p.into_boxed_slice();268269let mut i = 0;270for value in m.values() {271match i {2720 => assert_eq!(*value, 12),2731 => assert_eq!(*value, 33),274_ => panic!(),275}276i += 1;277}278i = 0;279for value_mut in m.values_mut() {280match i {2810 => assert_eq!(*value_mut, 12),2821 => assert_eq!(*value_mut, 33),283_ => panic!(),284}285i += 1;286}287}288289#[test]290fn values_rev() {291let mut p: PrimaryMap<E, usize> = PrimaryMap::new();292p.push(12);293p.push(33);294let mut m = p.into_boxed_slice();295296let mut i = 2;297for value in m.values().rev() {298i -= 1;299match i {3000 => assert_eq!(*value, 12),3011 => assert_eq!(*value, 33),302_ => panic!(),303}304}305i = 2;306for value_mut in m.values_mut().rev() {307i -= 1;308match i {3090 => assert_eq!(*value_mut, 12),3101 => assert_eq!(*value_mut, 33),311_ => panic!(),312}313}314}315}316317318