aboutsummaryrefslogtreecommitdiff
path: root/common/object/src/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'common/object/src/lib.rs')
-rw-r--r--common/object/src/lib.rs39
1 files changed, 34 insertions, 5 deletions
diff --git a/common/object/src/lib.rs b/common/object/src/lib.rs
index bb21942..7c97bee 100644
--- a/common/object/src/lib.rs
+++ b/common/object/src/lib.rs
@@ -12,14 +12,17 @@ mod registry;
mod tests;
mod value;
pub use buffer::*;
+use bytemuck::NoUninit;
pub use registry::*;
pub use value::*;
use std::marker::PhantomData;
#[repr(transparent)]
-#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
+#[derive(NoUninit, Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
pub struct Tag(pub u32);
+
+#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
pub struct TypedTag<T>(pub Tag, pub PhantomData<T>);
#[derive(Debug, Clone, Copy)]
@@ -94,12 +97,19 @@ impl<'a> Object<'a> {
pub fn get<'b: 'a, T: Value<'b>>(&'b self, tag: TypedTag<T>) -> Option<T> {
self.get_typed(self.find_field(tag.0)?)
}
- pub fn keys<'b: 'a>(&'b self) -> ObjectIter<'b> {
- ObjectIter {
+ pub fn keys<'b: 'a>(&'b self) -> KeysIter<'b> {
+ KeysIter {
object: self,
index: 0,
}
}
+ pub fn entries<'b: 'a, T>(&'b self) -> EntriesIter<'b, T> {
+ EntriesIter {
+ object: self,
+ index: 0,
+ ty: PhantomData,
+ }
+ }
pub fn iter<'b: 'a, T>(&'b self, tag: TypedTag<T>) -> FieldIter<'b, T> {
FieldIter {
object: self,
@@ -161,11 +171,11 @@ impl<'a> Object<'a> {
}
}
-pub struct ObjectIter<'a> {
+pub struct KeysIter<'a> {
object: &'a Object<'a>,
index: usize,
}
-impl Iterator for ObjectIter<'_> {
+impl Iterator for KeysIter<'_> {
type Item = Tag;
fn next(&mut self) -> Option<Self::Item> {
if self.index >= self.object.tags.len() {
@@ -177,6 +187,25 @@ impl Iterator for ObjectIter<'_> {
}
}
+pub struct EntriesIter<'a, T> {
+ object: &'a Object<'a>,
+ index: usize,
+ ty: PhantomData<T>,
+}
+impl<'a, T: Value<'a>> Iterator for EntriesIter<'a, T> {
+ type Item = (Tag, T);
+ fn next(&mut self) -> Option<Self::Item> {
+ if self.index >= self.object.tags.len() {
+ return None;
+ } else {
+ let value = self.object.get_typed(self.index)?; //? This ends the iterator early if there is any invalid field
+ let tag = self.object.tags[self.index];
+ self.index += 1;
+ Some((Tag(tag), value))
+ }
+ }
+}
+
pub struct FieldIter<'a, T> {
object: &'a Object<'a>,
index: usize,