Skip to content

Commit

Permalink
renamed extend() to union() and merge() to intersection() for various…
Browse files Browse the repository at this point in the history
… iterators
  • Loading branch information
proycon committed Nov 18, 2023
1 parent 3758d57 commit 85701ee
Show file tree
Hide file tree
Showing 4 changed files with 50 additions and 21 deletions.
17 changes: 10 additions & 7 deletions src/api/annotation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -166,6 +166,7 @@ impl<'store> ResultItem<'store, Annotation> {

/// Returns the (single!) resource the annotation points to. Only works if this annotation targets using a [`Selector::TextSelector`],
/// [`Selector::ResourceSelector`] or [`Selector::AnnotationSelector`], and not for complex selectors.
/// Use [`Self::resources()`] if want to iterate over all resources instead.
/// AnnotationSelectors are followed recursively if needed.
pub fn resource(&self) -> Option<ResultItem<'store, TextResource>> {
match self.as_ref().target() {
Expand Down Expand Up @@ -629,7 +630,7 @@ impl<'store> AnnotationsIter<'store> {
pub fn filter_annotations(mut self, annotations: AnnotationsIter<'store>) -> Self {
if self.iter.is_some() {
if annotations.iter.is_some() {
self.iter = Some(self.iter.unwrap().merge(annotations.iter.unwrap()));
self.iter = Some(self.iter.unwrap().intersection(annotations.iter.unwrap()));
} else {
//invalidate the iterator, there will be no results
self.abort();
Expand Down Expand Up @@ -817,21 +818,23 @@ impl<'store> AnnotationsIter<'store> {
}

/// Produces the union between two annotation iterators
/// Any constraints on either iterator remain valid!
pub fn extend(mut self, other: AnnotationsIter<'store>) -> AnnotationsIter<'store> {
/// Any filters on either iterator remain valid!
pub fn union(mut self, other: AnnotationsIter<'store>) -> AnnotationsIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.iter = Some(self.iter.unwrap().extend(other.iter.unwrap()));
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().union(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
self
}

/// Produces the intersection between two annotation iterators
/// Any constraints on either iterator remain valid!
pub fn merge(mut self, other: AnnotationsIter<'store>) -> AnnotationsIter<'store> {
/// Any filters on either iterator remain valid!
pub fn intersection(mut self, other: AnnotationsIter<'store>) -> AnnotationsIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.iter = Some(self.iter.unwrap().extend(other.iter.unwrap()));
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().intersection(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
Expand Down
16 changes: 9 additions & 7 deletions src/api/annotationdata.rs
Original file line number Diff line number Diff line change
Expand Up @@ -298,7 +298,7 @@ impl<'store> DataIter<'store> {
///
/// You can cast any existing iterator that produces [`ResultItem<AnnotationData>`] to a [`DataIter`] using [`DataIter::from_iter()`].
pub fn filter_data(self, data: DataIter<'store>) -> Self {
self.merge(data)
self.intersection(data)
}

/// Find and filter data. Returns an iterator over the data.
Expand Down Expand Up @@ -447,21 +447,23 @@ impl<'store> DataIter<'store> {
}

/// Produces the union between two data iterators
/// Any constraints on either iterator remain valid!
pub fn extend(mut self, other: DataIter<'store>) -> DataIter<'store> {
/// Any filters on either iterator remain valid!
pub fn union(mut self, other: DataIter<'store>) -> DataIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.iter = Some(self.iter.unwrap().extend(other.iter.unwrap()));
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().union(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
self
}

/// Produces the intersection between two data iterators
/// Any constraints on either iterator remain valid!
pub fn merge(mut self, other: DataIter<'store>) -> DataIter<'store> {
/// Any filters on either iterator remain valid!
pub fn intersection(mut self, other: DataIter<'store>) -> DataIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.iter = Some(self.iter.unwrap().merge(other.iter.unwrap()));
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().intersection(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
Expand Down
26 changes: 25 additions & 1 deletion src/api/resources.rs
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ impl<'store> ResultItem<'store, TextResource> {
/// Use `annotations_as_metadata()` or `annotations_on_text()` instead if you want to differentiate the two.
pub fn annotations(&self) -> AnnotationsIter<'store> {
self.annotations_as_metadata()
.extend(self.annotations_on_text())
.union(self.annotations_on_text())
}

/// Returns an iterator over all text selections that are marked in this resource (i.e. there are one or more annotations on it).
Expand Down Expand Up @@ -306,6 +306,30 @@ impl<'store> ResourcesIter<'store> {
self
}

/// Produces the union between two resource iterators
/// Any filters on either iterator remain valid!
pub fn union(mut self, other: ResourcesIter<'store>) -> ResourcesIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().union(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
self
}

/// Produces the intersection between two resource iterators
/// Any filters on either iterator remain valid!
pub fn intersection(mut self, other: ResourcesIter<'store>) -> ResourcesIter<'store> {
if self.iter.is_some() && other.iter.is_some() {
self.filters.extend(other.filters.into_iter());
self.iter = Some(self.iter.unwrap().intersection(other.iter.unwrap()));
} else if self.iter.is_none() {
return other;
}
self
}

/// Does this iterator return items in sorted order?
pub fn returns_sorted(&self) -> bool {
if let Some(iter) = self.iter.as_ref() {
Expand Down
12 changes: 6 additions & 6 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -267,7 +267,7 @@ where

/// Merges another IntersectionIter into the current one. This effectively
/// iterates over the intersection of both.
pub(crate) fn merge(mut self, other: IntersectionIter<'a, T>) -> Self {
pub(crate) fn intersection(mut self, other: IntersectionIter<'a, T>) -> Self {
for source in other.sources {
if source.array.is_some() {
self = self.with(source.array.unwrap(), source.sorted);
Expand All @@ -283,7 +283,7 @@ where

/// Extends this iterator with another one. This is a *union* and not an *intersection*.
/// However, all additional constraints on either iterator are preserved (and those are intersections).
pub(crate) fn extend(mut self, mut other: IntersectionIter<'a, T>) -> Self {
pub(crate) fn union(mut self, mut other: IntersectionIter<'a, T>) -> Self {
//edge-cases first:
if self.sources.is_empty() {
return other;
Expand Down Expand Up @@ -557,21 +557,21 @@ mod test {
}

#[test]
fn test_intersectioniter_merge() {
fn test_intersectioniter_intersection() {
let mut iter = IntersectionIter::new(Cow::Owned(vec![1, 2, 3, 4, 5]), true);
iter = iter.with(Cow::Owned(vec![1, 3, 5]), true);
let iter2 = IntersectionIter::new(Cow::Owned(vec![5, 6]), true);
iter = iter.merge(iter2);
iter = iter.intersection(iter2);
iter = iter.with(Cow::Owned(vec![5]), true);
let v: Vec<_> = iter.collect();
assert_eq!(v, vec![5]);
}

#[test]
fn test_intersectioniter_extend() {
fn test_intersectioniter_union() {
let mut iter = IntersectionIter::new(Cow::Owned(vec![1, 2, 3, 4, 5]), true);
let iter2 = IntersectionIter::new(Cow::Owned(vec![6, 7]), true);
iter = iter.extend(iter2);
iter = iter.union(iter2);
let v: Vec<_> = iter.collect();
assert_eq!(v, vec![1, 2, 3, 4, 5, 6, 7]);
}
Expand Down

0 comments on commit 85701ee

Please sign in to comment.