Add an EntityRef::wrap() method.

This is the opposite of unwrap(). It converts the ad-hoc null references like
NO_EBB and NO_INST into the more standard Option<Ebb> type which unfortunately
takes twice as much space in data structures.
This commit is contained in:
Jakob Stoklund Olesen
2016-07-18 14:25:28 -07:00
parent 32f40168b5
commit c76ba3a7f6

View File

@@ -11,13 +11,31 @@ use std::ops::{Index, IndexMut};
/// A type wrapping a small integer index should implement `EntityRef` so it can be used as the key
/// of an `EntityMap`.
pub trait EntityRef: Copy {
pub trait EntityRef: Copy + Eq {
/// Create a new entity reference from a small integer.
/// This should crash if the requested index is not representable.
fn new(usize) -> Self;
/// Get the index that was used to create this entity reference.
fn index(self) -> usize;
/// Convert an `EntityRef` to an `Optional<EntityRef>` by using the default value as the null
/// reference.
///
/// Entity references are often used in compact data structures like linked lists where a
/// sentinel 'null' value is needed. Normally we would use an `Optional` for that, but
/// currently that uses twice the memory of a plain `EntityRef`.
///
/// This method is called `wrap()` because it is the inverse of `unwrap()`.
fn wrap(self) -> Option<Self>
where Self: Default
{
if self == Self::default() {
None
} else {
Some(self)
}
}
}
/// A mapping `K -> V` for densely indexed entity references.
@@ -91,7 +109,7 @@ mod tests {
use super::*;
// EntityRef impl for testing.
#[derive(Clone, Copy)]
#[derive(Clone, Copy, PartialEq, Eq)]
struct E(u32);
impl EntityRef for E {