1#![deny(missing_docs)]
2#![allow(clippy::needless_lifetimes)]
3
4use crate::merge_state::{
6 BoolOpMergeState, InPlaceMergeState, InPlaceMergeStateRef, MergeStateMut, SmallVecMergeState,
7};
8use binary_merge::{MergeOperation, MergeState};
9use core::cmp::Ordering;
10use core::fmt::Debug;
11use core::ops::{
12 BitAnd, BitAndAssign, BitOr, BitOrAssign, BitXor, BitXorAssign, Bound, Not, Range, RangeFrom,
13 RangeTo, Sub, SubAssign,
14};
15use ref_cast::{ref_cast_custom, RefCastCustom};
16use smallvec::{Array, SmallVec};
17use std::borrow::Borrow;
18use std::num::*;
19use std::ops::{Deref, RangeBounds, RangeFull};
20#[cfg(feature = "serde")]
21use {
22 core::{fmt, marker::PhantomData},
23 serde::{
24 de::{Deserialize, Deserializer, SeqAccess, Visitor},
25 ser::{Serialize, SerializeSeq, Serializer},
26 },
27};
28
29pub struct RangeSet<A: Array>(SmallVec<A>);
95
96impl<T, A: Array<Item = T>> Default for RangeSet<A> {
97 fn default() -> Self {
98 Self(Default::default())
99 }
100}
101
102impl<T, A: Array<Item = T>> Deref for RangeSet<A> {
103 type Target = RangeSetRef<T>;
104
105 fn deref(&self) -> &Self::Target {
106 RangeSetRef::new_unchecked_impl(&self.0)
107 }
108}
109
110impl<T, A: Array<Item = T>> AsRef<RangeSetRef<T>> for RangeSet<A> {
111 fn as_ref(&self) -> &RangeSetRef<T> {
112 RangeSetRef::new_unchecked_impl(&self.0)
113 }
114}
115
116impl<T, A: Array<Item = T>> Borrow<RangeSetRef<T>> for RangeSet<A> {
117 fn borrow(&self) -> &RangeSetRef<T> {
118 RangeSetRef::new_unchecked_impl(&self.0)
119 }
120}
121
122#[derive(Clone)]
127pub enum RangeSetRange<T> {
128 Range(Range<T>),
130 RangeFrom(RangeFrom<T>),
132}
133
134impl<T: Clone> RangeSetRange<&T> {
135 pub fn cloned(&self) -> RangeSetRange<T> {
137 match self {
138 RangeSetRange::Range(r) => RangeSetRange::Range(r.start.clone()..r.end.clone()),
139 RangeSetRange::RangeFrom(r) => RangeSetRange::RangeFrom(r.start.clone()..),
140 }
141 }
142}
143
144impl<T> From<Range<T>> for RangeSetRange<T> {
145 fn from(r: Range<T>) -> Self {
146 RangeSetRange::Range(r)
147 }
148}
149
150impl<T> From<RangeFrom<T>> for RangeSetRange<T> {
151 fn from(r: RangeFrom<T>) -> Self {
152 RangeSetRange::RangeFrom(r)
153 }
154}
155
156impl<T: RangeSetEntry, A: Array<Item = T>> From<RangeSetRange<T>> for RangeSet<A> {
157 fn from(value: RangeSetRange<T>) -> Self {
158 match value {
159 RangeSetRange::Range(r) => RangeSet::from(r),
160 RangeSetRange::RangeFrom(r) => RangeSet::from(r),
161 }
162 }
163}
164
165impl<T: Debug> Debug for RangeSetRange<T> {
166 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
167 match self {
168 RangeSetRange::Range(r) => r.fmt(f),
169 RangeSetRange::RangeFrom(r) => r.fmt(f),
170 }
171 }
172}
173
174impl<T> RangeBounds<T> for RangeSetRange<T> {
175 fn start_bound(&self) -> Bound<&T> {
176 match self {
177 RangeSetRange::Range(r) => r.start_bound(),
178 RangeSetRange::RangeFrom(r) => r.start_bound(),
179 }
180 }
181
182 fn end_bound(&self) -> Bound<&T> {
183 match self {
184 RangeSetRange::Range(r) => r.end_bound(),
185 RangeSetRange::RangeFrom(r) => r.end_bound(),
186 }
187 }
188}
189
190impl<A: Array> Clone for RangeSet<A>
191where
192 A::Item: Clone,
193{
194 fn clone(&self) -> Self {
195 Self(self.0.clone())
196 }
197}
198
199impl<A: Array, R: AsRef<RangeSetRef<A::Item>>> PartialEq<R> for RangeSet<A>
200where
201 A::Item: RangeSetEntry,
202{
203 fn eq(&self, that: &R) -> bool {
204 self.boundaries() == that.as_ref().boundaries()
205 }
206}
207
208impl<A: Array> Eq for RangeSet<A> where A::Item: Eq + RangeSetEntry {}
209
210pub type RangeSet2<T> = RangeSet<[T; 2]>;
212
213impl<T: Debug, A: Array<Item = T>> Debug for RangeSet<A> {
214 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
215 write!(f, "RangeSet{{")?;
216 for (i, r) in self.iter().enumerate() {
217 if i > 0 {
218 write!(f, ", ")?;
219 }
220 write!(f, "{r:?}")?;
221 }
222 write!(f, "}}")
223 }
224}
225
226pub struct Iter<'a, T>(&'a [T]);
228
229impl<'a, T> Iterator for Iter<'a, T> {
230 type Item = RangeSetRange<&'a T>;
231
232 fn next(&mut self) -> Option<Self::Item> {
233 let bounds = self.0;
234 if !bounds.is_empty() {
235 Some(if bounds.len() == 1 {
236 self.0 = &bounds[1..];
237 RangeSetRange::from(&bounds[0]..)
238 } else {
239 self.0 = &bounds[2..];
240 RangeSetRange::from(&bounds[0]..&bounds[1])
241 })
242 } else {
243 None
244 }
245 }
246}
247
248#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, RefCastCustom)]
250#[repr(transparent)]
251pub struct RangeSetRef<T>([T]);
252
253impl<T> Default for &RangeSetRef<T> {
254 fn default() -> Self {
255 RangeSetRef::new_unchecked_impl(&[])
256 }
257}
258
259impl<T> RangeSetRef<T> {
260 pub const fn empty() -> &'static Self {
262 RangeSetRef::new_unchecked_impl(&[])
263 }
264
265 pub const fn single(value: &T) -> &Self {
270 RangeSetRef::new_unchecked_impl(std::slice::from_ref(value))
271 }
272
273 pub fn new(boundaries: &[T]) -> Option<&Self>
279 where
280 T: Ord,
281 {
282 if is_strictly_sorted(boundaries) {
283 Some(Self::new_unchecked_impl(boundaries))
284 } else {
285 None
286 }
287 }
288
289 pub fn split(&self, at: T) -> (&Self, &Self)
301 where
302 T: Ord,
303 {
304 let (left, right) = split(&self.0, at);
305 (
306 Self::new_unchecked_impl(left),
307 Self::new_unchecked_impl(right),
308 )
309 }
310
311 #[cfg(feature = "new_unchecked")]
314 pub const fn new_unchecked(boundaries: &[T]) -> &Self {
315 Self::new_unchecked_impl(boundaries)
316 }
317
318 #[ref_cast_custom]
319 const fn new_unchecked_impl(boundaries: &[T]) -> &Self;
320
321 pub const fn boundaries(&self) -> &[T] {
323 &self.0
324 }
325
326 pub fn contains(&self, value: &T) -> bool
328 where
329 T: Ord,
330 {
331 match self.boundaries().binary_search(value) {
332 Ok(index) => !is_odd(index),
333 Err(index) => is_odd(index),
334 }
335 }
336
337 pub const fn is_empty(&self) -> bool {
339 self.boundaries().is_empty()
340 }
341
342 pub fn is_all(&self) -> bool
344 where
345 T: RangeSetEntry,
346 {
347 self.boundaries().len() == 1 && self.boundaries()[0].is_min_value()
348 }
349
350 pub fn intersects(&self, that: &RangeSetRef<T>) -> bool
355 where
356 T: Ord,
357 {
358 !self.is_disjoint(that)
359 }
360
361 pub fn is_disjoint(&self, that: &RangeSetRef<T>) -> bool
363 where
364 T: Ord,
365 {
366 !RangeSetBoolOpMergeState::merge(self.boundaries(), that.boundaries(), IntersectionOp::<0>)
367 }
368
369 pub fn is_subset(&self, that: &RangeSetRef<T>) -> bool
373 where
374 T: Ord,
375 {
376 !RangeSetBoolOpMergeState::merge(self.boundaries(), that.boundaries(), DiffOp::<0>)
377 }
378
379 pub fn is_superset(&self, that: &RangeSetRef<T>) -> bool
383 where
384 T: Ord,
385 {
386 !RangeSetBoolOpMergeState::merge(that.boundaries(), self.boundaries(), DiffOp::<0>)
387 }
388
389 pub fn iter(&self) -> Iter<T> {
391 Iter(self.boundaries())
392 }
393
394 pub fn intersection<A>(&self, that: &RangeSetRef<T>) -> RangeSet<A>
396 where
397 A: Array<Item = T>,
398 T: Ord + Clone,
399 {
400 RangeSet::new_unchecked_impl(VecMergeState::merge(
401 self.boundaries(),
402 that.boundaries(),
403 IntersectionOp::<{ usize::MAX }>,
404 ))
405 }
406
407 pub fn union<A>(&self, that: &RangeSetRef<T>) -> RangeSet<A>
409 where
410 A: Array<Item = T>,
411 T: Ord + Clone,
412 {
413 RangeSet::new_unchecked_impl(VecMergeState::merge(
414 self.boundaries(),
415 that.boundaries(),
416 UnionOp,
417 ))
418 }
419
420 pub fn difference<A>(&self, that: &RangeSetRef<T>) -> RangeSet<A>
422 where
423 A: Array<Item = T>,
424 T: Ord + Clone,
425 {
426 RangeSet::new_unchecked_impl(VecMergeState::merge(
427 self.boundaries(),
428 that.boundaries(),
429 DiffOp::<{ usize::MAX }>,
430 ))
431 }
432
433 pub fn symmetric_difference<A>(&self, that: &RangeSetRef<T>) -> RangeSet<A>
435 where
436 A: Array<Item = T>,
437 T: Ord + Clone,
438 {
439 RangeSet::new_unchecked_impl(VecMergeState::merge(
440 self.boundaries(),
441 that.boundaries(),
442 XorOp,
443 ))
444 }
445}
446
447#[cfg(feature = "rkyv")]
448impl<T> Deref for ArchivedRangeSet<T> {
449 type Target = RangeSetRef<T>;
450
451 fn deref(&self) -> &Self::Target {
452 RangeSetRef::new_unchecked(&self.0)
453 }
454}
455
456#[cfg(feature = "rkyv")]
457impl<T> AsRef<RangeSetRef<T>> for ArchivedRangeSet<T> {
458 fn as_ref(&self) -> &RangeSetRef<T> {
459 RangeSetRef::new_unchecked(&self.0)
460 }
461}
462
463#[cfg(feature = "rkyv")]
464impl<T> Borrow<RangeSetRef<T>> for ArchivedRangeSet<T> {
465 fn borrow(&self) -> &RangeSetRef<T> {
466 RangeSetRef::new_unchecked(&self.0)
467 }
468}
469
470pub trait RangeSetEntry: Ord {
474 fn min_value() -> Self;
476
477 fn is_min_value(&self) -> bool;
481}
482
483macro_rules! entry_instance {
484 ($t:tt) => {
485 impl RangeSetEntry for $t {
486
487 fn min_value() -> Self {
488 $t::MIN
489 }
490
491 fn is_min_value(&self) -> bool {
492 *self == $t::MIN
493 }
494 }
495 };
496 ($t:tt, $($rest:tt),+) => {
497 entry_instance!($t);
498 entry_instance!($( $rest ),*);
499 }
500}
501
502macro_rules! non_zero_u_entry_instance {
503 ($t:tt) => {
504 impl RangeSetEntry for $t {
505
506 fn min_value() -> Self {
507 $t::new(1).unwrap()
508 }
509
510 fn is_min_value(&self) -> bool {
511 *self == $t::new(1).unwrap()
512 }
513 }
514 };
515 ($t:tt, $($rest:tt),+) => {
516 non_zero_u_entry_instance!($t);
517 non_zero_u_entry_instance!($( $rest ),*);
518 }
519}
520
521entry_instance!(u8, u16, u32, u64, u128, usize);
522entry_instance!(i8, i16, i32, i64, i128, isize);
523non_zero_u_entry_instance!(
524 NonZeroU8,
525 NonZeroU16,
526 NonZeroU32,
527 NonZeroU64,
528 NonZeroU128,
529 NonZeroUsize
530);
531
532impl<T: Ord> RangeSetEntry for Option<T> {
533 fn min_value() -> Self {
534 None
535 }
536
537 fn is_min_value(&self) -> bool {
538 self.is_none()
539 }
540}
541
542impl RangeSetEntry for String {
543 fn min_value() -> Self {
544 "".to_owned()
545 }
546
547 fn is_min_value(&self) -> bool {
548 self.is_empty()
549 }
550}
551
552impl RangeSetEntry for &str {
553 fn min_value() -> Self {
554 ""
555 }
556
557 fn is_min_value(&self) -> bool {
558 self.is_empty()
559 }
560}
561
562impl<T: Ord> RangeSetEntry for Vec<T> {
563 fn min_value() -> Self {
564 Vec::new()
565 }
566
567 fn is_min_value(&self) -> bool {
568 self.is_empty()
569 }
570}
571
572impl<T: Ord> RangeSetEntry for &[T] {
573 fn min_value() -> Self {
574 &[]
575 }
576
577 fn is_min_value(&self) -> bool {
578 self.is_empty()
579 }
580}
581
582impl<T, A: Array<Item = T>> RangeSet<A> {
583 pub fn new(boundaries: SmallVec<A>) -> Option<Self>
589 where
590 A::Item: Ord,
591 {
592 if is_strictly_sorted(boundaries.as_ref()) {
593 Some(Self::new_unchecked_impl(boundaries))
594 } else {
595 None
596 }
597 }
598
599 #[cfg(feature = "new_unchecked")]
602 pub fn new_unchecked(boundaries: SmallVec<A>) -> Self {
603 Self::new_unchecked_impl(boundaries)
604 }
605
606 fn new_unchecked_impl(boundaries: SmallVec<A>) -> Self {
608 RangeSet(boundaries)
609 }
610
611 pub fn iter(&self) -> Iter<T> {
613 Iter(self.0.as_ref())
614 }
615
616 pub fn into_inner(self) -> SmallVec<A> {
618 self.0
619 }
620}
621
622impl<T: RangeSetEntry, A: Array<Item = T>> RangeSet<A> {
623 fn from_range_until(a: T) -> Self {
624 let mut t = SmallVec::new();
625 if !a.is_min_value() {
626 t.push(T::min_value());
627 t.push(a);
628 }
629 Self::new_unchecked_impl(t)
630 }
631 fn from_range_from(a: T) -> Self {
632 let mut t = SmallVec::new();
633 t.push(a);
634 Self::new_unchecked_impl(t)
635 }
636 pub fn empty() -> Self {
638 Self(SmallVec::new())
639 }
640 pub fn all() -> Self {
642 Self::from_range_from(T::min_value())
643 }
644}
645
646impl<T: RangeSetEntry + Clone, A: Array<Item = T>> RangeSet<A> {
647 pub fn intersection_with(&mut self, that: &RangeSetRef<T>) {
649 InPlaceMergeStateRef::merge(
650 &mut self.0,
651 &that.boundaries(),
652 IntersectionOp::<{ usize::MAX }>,
653 );
654 }
655 pub fn union_with(&mut self, that: &RangeSetRef<T>) {
657 InPlaceMergeStateRef::merge(&mut self.0, &that.boundaries(), UnionOp);
658 }
659 pub fn difference_with(&mut self, that: &RangeSetRef<T>) {
661 InPlaceMergeStateRef::merge(&mut self.0, &that.boundaries(), DiffOp::<{ usize::MAX }>);
662 }
663 pub fn symmetric_difference_with(&mut self, that: &RangeSetRef<T>) {
665 InPlaceMergeStateRef::merge(&mut self.0, &that.boundaries(), XorOp);
666 }
667}
668
669impl<T: RangeSetEntry, A: Array<Item = T>> From<bool> for RangeSet<A> {
670 fn from(value: bool) -> Self {
671 if value {
672 Self::all()
673 } else {
674 Self::empty()
675 }
676 }
677}
678
679impl<T: RangeSetEntry, A: Array<Item = T>> RangeSet<A> {
680 fn from_range(a: Range<T>) -> Self {
681 if a.start < a.end {
682 let mut t = SmallVec::new();
683 t.push(a.start);
684 t.push(a.end);
685 Self::new_unchecked_impl(t)
686 } else {
687 Self::empty()
688 }
689 }
690}
691
692impl<T: RangeSetEntry, A: Array<Item = T>> From<Range<T>> for RangeSet<A> {
693 fn from(value: Range<T>) -> Self {
694 Self::from_range(value)
695 }
696}
697
698impl<T: RangeSetEntry, A: Array<Item = T>> From<RangeFrom<T>> for RangeSet<A> {
699 fn from(value: RangeFrom<T>) -> Self {
700 Self::from_range_from(value.start)
701 }
702}
703
704impl<T: RangeSetEntry, A: Array<Item = T>> From<RangeTo<T>> for RangeSet<A> {
705 fn from(value: RangeTo<T>) -> Self {
706 Self::from_range_until(value.end)
707 }
708}
709
710impl<T: RangeSetEntry, A: Array<Item = T>> From<RangeFull> for RangeSet<A> {
711 fn from(_: RangeFull) -> Self {
712 Self::all()
713 }
714}
715
716impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitAnd<RangeSet<A>> for RangeSet<A> {
720 type Output = RangeSet<A>;
721 fn bitand(self, that: RangeSet<A>) -> Self::Output {
722 self.intersection(&that)
723 }
724}
725
726impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitAnd<&RangeSet<A>> for RangeSet<A> {
727 type Output = RangeSet<A>;
728 fn bitand(self, that: &RangeSet<A>) -> Self::Output {
729 self.intersection(that)
730 }
731}
732
733impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitAnd<RangeSet<A>> for &RangeSet<A> {
734 type Output = RangeSet<A>;
735 fn bitand(self, that: RangeSet<A>) -> Self::Output {
736 self.intersection(&that)
737 }
738}
739
740impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitAnd<&RangeSet<A>> for &RangeSet<A> {
741 type Output = RangeSet<A>;
742 fn bitand(self, that: &RangeSet<A>) -> Self::Output {
743 self.intersection(that)
744 }
745}
746
747impl<T: Ord, A: Array<Item = T>> BitAndAssign for RangeSet<A> {
748 fn bitand_assign(&mut self, that: Self) {
749 InPlaceMergeState::merge(&mut self.0, that.0, IntersectionOp::<{ usize::MAX }>);
750 }
751}
752
753impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitOr<RangeSet<A>> for RangeSet<A> {
757 type Output = RangeSet<A>;
758 fn bitor(self, that: RangeSet<A>) -> Self::Output {
759 self.union(&that)
760 }
761}
762
763impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitOr<&RangeSet<A>> for RangeSet<A> {
764 type Output = RangeSet<A>;
765 fn bitor(self, that: &RangeSet<A>) -> Self::Output {
766 self.union(that)
767 }
768}
769
770impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitOr<RangeSet<A>> for &RangeSet<A> {
771 type Output = RangeSet<A>;
772 fn bitor(self, that: RangeSet<A>) -> Self::Output {
773 self.union(&that)
774 }
775}
776
777impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitOr<&RangeSet<A>> for &RangeSet<A> {
778 type Output = RangeSet<A>;
779 fn bitor(self, that: &RangeSet<A>) -> Self::Output {
780 self.union(that)
781 }
782}
783
784impl<T: Ord, A: Array<Item = T>> BitOrAssign for RangeSet<A> {
785 fn bitor_assign(&mut self, that: Self) {
786 InPlaceMergeState::merge(&mut self.0, that.0, UnionOp);
787 }
788}
789
790impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitXor<RangeSet<A>> for RangeSet<A> {
794 type Output = RangeSet<A>;
795 fn bitxor(self, that: RangeSet<A>) -> Self::Output {
796 self.symmetric_difference(&that)
797 }
798}
799
800impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitXor<&RangeSet<A>> for RangeSet<A> {
801 type Output = RangeSet<A>;
802 fn bitxor(self, that: &RangeSet<A>) -> Self::Output {
803 self.symmetric_difference(that)
804 }
805}
806
807impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitXor<RangeSet<A>> for &RangeSet<A> {
808 type Output = RangeSet<A>;
809 fn bitxor(self, that: RangeSet<A>) -> Self::Output {
810 self.symmetric_difference(&that)
811 }
812}
813
814impl<T: RangeSetEntry + Clone, A: Array<Item = T>> BitXor<&RangeSet<A>> for &RangeSet<A> {
815 type Output = RangeSet<A>;
816 fn bitxor(self, that: &RangeSet<A>) -> Self::Output {
817 self.symmetric_difference(that)
818 }
819}
820
821impl<T: RangeSetEntry, A: Array<Item = T>> BitXorAssign for RangeSet<A> {
822 fn bitxor_assign(&mut self, that: Self) {
823 InPlaceMergeState::merge(&mut self.0, that.0, XorOp);
824 }
825}
826
827impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Sub<RangeSet<A>> for RangeSet<A> {
831 type Output = RangeSet<A>;
832 fn sub(self, that: RangeSet<A>) -> Self::Output {
833 self.difference(&that)
834 }
835}
836
837impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Sub<&RangeSet<A>> for RangeSet<A> {
838 type Output = RangeSet<A>;
839 fn sub(self, that: &RangeSet<A>) -> Self::Output {
840 self.difference(that)
841 }
842}
843
844impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Sub<RangeSet<A>> for &RangeSet<A> {
845 type Output = RangeSet<A>;
846 fn sub(self, that: RangeSet<A>) -> Self::Output {
847 self.difference(&that)
848 }
849}
850
851impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Sub<&RangeSet<A>> for &RangeSet<A> {
852 type Output = RangeSet<A>;
853 fn sub(self, that: &RangeSet<A>) -> Self::Output {
854 self.difference(that)
855 }
856}
857
858impl<T: Ord, A: Array<Item = T>> SubAssign for RangeSet<A> {
859 fn sub_assign(&mut self, that: Self) {
860 InPlaceMergeState::merge(&mut self.0, that.0, DiffOp::<{ usize::MAX }>);
861 }
862}
863
864impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Not for RangeSet<A> {
868 type Output = RangeSet<A>;
869 fn not(mut self) -> Self::Output {
870 match self.0.first() {
871 Some(x) if x.is_min_value() => {
872 self.0.remove(0);
873 }
874 _ => {
875 self.0.insert(0, T::min_value());
876 }
877 }
878 self
879 }
880}
881
882impl<T: RangeSetEntry + Clone, A: Array<Item = T>> Not for &RangeSet<A> {
886 type Output = RangeSet<A>;
887 fn not(self) -> Self::Output {
888 self ^ &RangeSet::all()
889 }
890}
891
892struct RangeSetBoolOpMergeState<'a, T> {
893 inner: BoolOpMergeState<'a, T, T>,
894}
895
896impl<'a, T> RangeSetBoolOpMergeState<'a, T> {
897 fn merge<O: MergeOperation<Self>>(a: &'a [T], b: &'a [T], o: O) -> bool {
898 let mut state = Self {
899 inner: BoolOpMergeState::new(a, b),
900 };
901 o.merge(&mut state);
902 state.inner.result()
903 }
904}
905
906impl<'a, T> MergeStateMut for RangeSetBoolOpMergeState<'a, T> {
907 fn advance_a(&mut self, n: usize, copy: bool) -> bool {
908 self.inner.advance_a(n, copy)
909 }
910 fn advance_b(&mut self, n: usize, copy: bool) -> bool {
911 self.inner.advance_b(n, copy)
912 }
913 fn ac(&self) -> bool {
914 self.inner.ac()
915 }
916 fn bc(&self) -> bool {
917 self.inner.bc()
918 }
919}
920
921impl<'a, T> MergeState for RangeSetBoolOpMergeState<'a, T> {
922 type A = T;
923 type B = T;
924 fn a_slice(&self) -> &[T] {
925 self.inner.a_slice()
926 }
927 fn b_slice(&self) -> &[T] {
928 self.inner.b_slice()
929 }
930}
931
932struct VecMergeState<'a, T, A: Array> {
933 inner: SmallVecMergeState<'a, T, T, A>,
934}
935
936impl<'a, T: Clone, A: Array<Item = T>> VecMergeState<'a, T, A> {
937 fn merge<O: MergeOperation<Self>>(a: &'a [T], b: &'a [T], o: O) -> SmallVec<A> {
938 let mut state = Self {
939 inner: SmallVecMergeState::new(a, b, SmallVec::new()),
940 };
941 o.merge(&mut state);
942 state.inner.result()
943 }
944}
945
946impl<'a, T: Clone, A: Array<Item = T>> MergeStateMut for VecMergeState<'a, T, A> {
947 fn advance_a(&mut self, n: usize, copy: bool) -> bool {
948 self.inner.advance_a(n, copy)
949 }
950 fn advance_b(&mut self, n: usize, copy: bool) -> bool {
951 self.inner.advance_b(n, copy)
952 }
953
954 fn ac(&self) -> bool {
955 self.inner.ac()
956 }
957
958 fn bc(&self) -> bool {
959 self.inner.bc()
960 }
961}
962
963impl<'a, T, A: Array<Item = T>> MergeState for VecMergeState<'a, T, A> {
964 type A = T;
965 type B = T;
966 fn a_slice(&self) -> &[T] {
967 self.inner.a_slice()
968 }
969 fn b_slice(&self) -> &[T] {
970 self.inner.b_slice()
971 }
972}
973
974#[cfg(feature = "serde")]
975impl<T: Serialize, A: Array<Item = T>> Serialize for RangeSet<A> {
976 fn serialize<S: Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
977 let mut map = serializer.serialize_seq(Some(self.0.len()))?;
978 for x in self.0.iter() {
979 map.serialize_element(x)?;
980 }
981 map.end()
982 }
983}
984
985#[cfg(feature = "serde")]
986impl<'de, T: Deserialize<'de> + Ord, A: Array<Item = T>> Deserialize<'de> for RangeSet<A> {
987 fn deserialize<D: Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
988 deserializer.deserialize_seq(RangeSetVisitor {
989 phantom: PhantomData,
990 })
991 }
992}
993
994#[cfg(feature = "serde")]
995struct RangeSetVisitor<T, A> {
996 phantom: PhantomData<(T, A)>,
997}
998
999#[cfg(feature = "serde")]
1000impl<'de, T, A: Array<Item = T>> Visitor<'de> for RangeSetVisitor<T, A>
1001where
1002 T: Deserialize<'de> + Ord,
1003{
1004 type Value = RangeSet<A>;
1005
1006 fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
1007 formatter.write_str("a sequence")
1008 }
1009
1010 fn visit_seq<B>(self, mut seq: B) -> Result<Self::Value, B::Error>
1011 where
1012 B: SeqAccess<'de>,
1013 {
1014 let len = seq.size_hint().unwrap_or(0);
1015 let mut boundaries: SmallVec<A> = SmallVec::with_capacity(len);
1016 while let Some(value) = seq.next_element::<A::Item>()? {
1017 boundaries.push(value);
1018 }
1019 boundaries.sort();
1020 boundaries.dedup();
1021 Ok(RangeSet(boundaries))
1022 }
1023}
1024
1025#[cfg(feature = "rkyv")]
1026impl<T, A> rkyv::Archive for RangeSet<A>
1027where
1028 T: rkyv::Archive,
1029 A: Array<Item = T>,
1030{
1031 type Archived = ArchivedRangeSet<<T as rkyv::Archive>::Archived>;
1032
1033 type Resolver = rkyv::vec::VecResolver;
1034
1035 unsafe fn resolve(&self, pos: usize, resolver: Self::Resolver, out: *mut Self::Archived) {
1036 rkyv::vec::ArchivedVec::resolve_from_slice(
1037 self.0.as_slice(),
1038 pos,
1039 resolver,
1040 &mut (*out).0 as *mut rkyv::vec::ArchivedVec<<T as rkyv::Archive>::Archived>,
1041 );
1042 }
1043}
1044
1045#[cfg(feature = "rkyv")]
1046impl<T, S, A> rkyv::Serialize<S> for RangeSet<A>
1047where
1048 T: rkyv::Archive + rkyv::Serialize<S>,
1049 S: rkyv::ser::ScratchSpace + rkyv::ser::Serializer,
1050 A: Array<Item = T>,
1051{
1052 fn serialize(&self, serializer: &mut S) -> Result<Self::Resolver, S::Error> {
1053 rkyv::vec::ArchivedVec::serialize_from_slice(self.0.as_ref(), serializer)
1054 }
1055}
1056
1057#[cfg(feature = "rkyv")]
1058impl<T, A, D> rkyv::Deserialize<RangeSet<A>, D> for ArchivedRangeSet<T::Archived>
1059where
1060 T: rkyv::Archive,
1061 A: Array<Item = T>,
1062 D: rkyv::Fallible + ?Sized,
1063 [T::Archived]: rkyv::DeserializeUnsized<[T], D>,
1064{
1065 fn deserialize(&self, deserializer: &mut D) -> Result<RangeSet<A>, D::Error> {
1066 let boundaries: Vec<T> = self.0.deserialize(deserializer)?;
1068 Ok(RangeSet(boundaries.into()))
1069 }
1070}
1071
1072#[cfg(feature = "rkyv")]
1074#[repr(transparent)]
1075pub struct ArchivedRangeSet<T>(rkyv::vec::ArchivedVec<T>);
1076
1077#[cfg(feature = "rkyv")]
1078impl<T: Debug> Debug for ArchivedRangeSet<T> {
1079 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1080 write!(f, "ArchivedRangeSet{{")?;
1081 for (i, r) in self.iter().enumerate() {
1082 if i > 0 {
1083 write!(f, ", ")?;
1084 }
1085 write!(f, "{r:?}")?;
1086 }
1087 write!(f, "}}")
1088 }
1089}
1090
1091#[cfg(feature = "rkyv_validated")]
1093#[derive(Debug)]
1094pub enum ArchivedRangeSetError {
1095 ValueCheckError,
1097 OrderCheckError,
1099}
1100
1101#[cfg(feature = "rkyv_validated")]
1102impl std::error::Error for ArchivedRangeSetError {}
1103
1104#[cfg(feature = "rkyv_validated")]
1105impl std::fmt::Display for ArchivedRangeSetError {
1106 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1107 write!(f, "{:?}", self)
1108 }
1109}
1110
1111#[cfg(feature = "rkyv_validated")]
1112impl<C: ?Sized, T> bytecheck::CheckBytes<C> for ArchivedRangeSet<T>
1113where
1114 T: Ord,
1115 bool: bytecheck::CheckBytes<C>,
1116 rkyv::vec::ArchivedVec<T>: bytecheck::CheckBytes<C>,
1117{
1118 type Error = ArchivedRangeSetError;
1119 unsafe fn check_bytes<'a>(
1120 value: *const Self,
1121 context: &mut C,
1122 ) -> Result<&'a Self, Self::Error> {
1123 let boundaries = &(*value).0;
1124 rkyv::vec::ArchivedVec::<T>::check_bytes(boundaries, context)
1125 .map_err(|_| ArchivedRangeSetError::ValueCheckError)?;
1126 if !boundaries
1127 .iter()
1128 .zip(boundaries.iter().skip(1))
1129 .all(|(a, b)| a < b)
1130 {
1131 return Err(ArchivedRangeSetError::OrderCheckError);
1132 };
1133 Ok(&*value)
1134 }
1135}
1136
1137struct UnionOp;
1138struct XorOp;
1139struct IntersectionOp<const T: usize>;
1140struct DiffOp<const T: usize>;
1141
1142impl<T: Ord, M: MergeStateMut<A = T, B = T>> MergeOperation<M> for UnionOp {
1143 fn from_a(&self, m: &mut M, n: usize) -> bool {
1144 m.advance_a(n, !m.bc())
1145 }
1146 fn from_b(&self, m: &mut M, n: usize) -> bool {
1147 m.advance_b(n, !m.ac())
1148 }
1149 fn collision(&self, m: &mut M) -> bool {
1150 m.advance_both(m.ac() == m.bc())
1151 }
1152 fn cmp(&self, a: &T, b: &T) -> Ordering {
1153 a.cmp(b)
1154 }
1155}
1156
1157impl<T: Ord, M: MergeStateMut<A = T, B = T>, const X: usize> MergeOperation<M>
1158 for IntersectionOp<X>
1159{
1160 fn from_a(&self, m: &mut M, n: usize) -> bool {
1161 m.advance_a(n, m.bc())
1162 }
1163 fn from_b(&self, m: &mut M, n: usize) -> bool {
1164 m.advance_b(n, m.ac())
1165 }
1166 fn collision(&self, m: &mut M) -> bool {
1167 m.advance_both(m.ac() == m.bc())
1168 }
1169 fn cmp(&self, a: &T, b: &T) -> Ordering {
1170 a.cmp(b)
1171 }
1172 const MCM_THRESHOLD: usize = X;
1173}
1174
1175impl<T: Ord, M: MergeStateMut<A = T, B = T>, const X: usize> MergeOperation<M> for DiffOp<X> {
1176 fn from_a(&self, m: &mut M, n: usize) -> bool {
1177 m.advance_a(n, !m.bc())
1178 }
1179 fn from_b(&self, m: &mut M, n: usize) -> bool {
1180 m.advance_b(n, m.ac())
1181 }
1182 fn collision(&self, m: &mut M) -> bool {
1183 m.advance_both(m.ac() != m.bc())
1184 }
1185 fn cmp(&self, a: &T, b: &T) -> Ordering {
1186 a.cmp(b)
1187 }
1188 const MCM_THRESHOLD: usize = X;
1189}
1190
1191impl<T: Ord, M: MergeStateMut<A = T, B = T>> MergeOperation<M> for XorOp {
1192 fn from_a(&self, m: &mut M, n: usize) -> bool {
1193 m.advance_a(n, true)
1194 }
1195 fn from_b(&self, m: &mut M, n: usize) -> bool {
1196 m.advance_b(n, true)
1197 }
1198 fn collision(&self, m: &mut M) -> bool {
1199 m.advance_both(false)
1200 }
1201 fn cmp(&self, a: &T, b: &T) -> Ordering {
1202 a.cmp(b)
1203 }
1204}
1205
1206#[inline]
1207fn is_odd(x: usize) -> bool {
1208 (x & 1) != 0
1209}
1210
1211#[inline]
1212fn is_even(x: usize) -> bool {
1213 (x & 1) == 0
1214}
1215
1216fn is_strictly_sorted<T: Ord>(ranges: &[T]) -> bool {
1217 for i in 0..ranges.len().saturating_sub(1) {
1218 if ranges[i] >= ranges[i + 1] {
1219 return false;
1220 }
1221 }
1222 true
1223}
1224
1225#[inline]
1234fn split<T: Ord>(ranges: &[T], at: T) -> (&[T], &[T]) {
1235 let l = ranges.len();
1236 let res = ranges.binary_search(&at);
1237 match res {
1238 Ok(i) if is_even(i) => {
1239 (&ranges[..i], &ranges[i..])
1241 }
1242 Err(i) if is_even(i) => {
1243 (&ranges[..i], &ranges[i..])
1245 }
1246 Ok(i) => {
1247 let sp = i.saturating_add(1).min(l);
1252 (&ranges[..i], &ranges[sp..])
1253 }
1254 Err(i) => {
1255 (&ranges[..i], &ranges[i.saturating_sub(1)..])
1261 }
1262 }
1263}
1264
1265#[allow(dead_code)]
1268fn contains<T: Ord>(boundaries: &[T], value: &T) -> bool {
1269 match boundaries.binary_search(value) {
1270 Ok(index) => !is_odd(index),
1271 Err(index) => is_odd(index),
1272 }
1273}
1274
1275#[allow(dead_code)]
1277fn intersects<T: Ord>(boundaries: &[T], range: Range<T>) -> bool {
1278 let (_, remaining) = split(boundaries, range.start);
1279 let (remaining, _) = split(remaining, range.end);
1280 !remaining.is_empty()
1283}
1284
1285#[cfg(test)]
1286mod util_tests {
1287 use std::{collections::BTreeSet, ops::Range};
1288
1289 use super::*;
1290 use proptest::prelude::*;
1291
1292 fn test_points(boundaries: impl IntoIterator<Item = u64>) -> BTreeSet<u64> {
1293 let mut res = BTreeSet::new();
1294 for x in boundaries {
1295 res.insert(x.saturating_sub(1));
1296 res.insert(x);
1297 res.insert(x.saturating_add(1));
1298 }
1299 res
1300 }
1301
1302 fn test_boundaries() -> impl Strategy<Value = (Vec<u64>, u64)> {
1303 proptest::collection::vec(any::<u64>(), 0..100).prop_flat_map(|mut v| {
1304 v.sort();
1305 v.dedup();
1306 let max_split = v
1308 .iter()
1309 .max()
1310 .cloned()
1311 .unwrap_or_default()
1312 .saturating_add(2);
1313 (Just(v), 0..max_split)
1314 })
1315 }
1316
1317 proptest! {
1318 #[test]
1319 fn test_split((boundaries, at) in test_boundaries()) {
1320 let (left, right) = split(&boundaries, at);
1321 for x in test_points(boundaries.clone()) {
1322 if x < at {
1324 prop_assert_eq!(contains(left, &x), contains(&boundaries, &x), "left must be like boundaries for x < at");
1325 } else {
1326 prop_assert_eq!(contains(right, &x), contains(&boundaries, &x), "right must be like boundaries for x >= at");
1327 }
1328 let nr = right.iter().filter(|x| x < &&at).count();
1330 prop_assert!(nr <= 1, "there must be at most one boundary before the split point");
1331 let nl = left.iter().filter(|x| x >= &&at).count();
1332 prop_assert!(nl == 0, "there must be no boundaries after the split point");
1333 }
1334 }
1335 }
1336
1337 #[test]
1338 fn test_split_0() {
1339 #[allow(clippy::type_complexity)]
1340 let cases: Vec<(&[u64], u64, (&[u64], &[u64]))> = vec![
1341 (&[0, 2], 0, (&[], &[0, 2])),
1342 (&[0, 2], 2, (&[0], &[])),
1343 (&[0, 2, 4], 2, (&[0], &[4])),
1344 (&[0, 2, 4], 4, (&[0, 2], &[4])),
1345 (&[0, 2, 4, 8], 2, (&[0], &[4, 8])),
1346 (&[0, 2, 4, 8], 4, (&[0, 2], &[4, 8])),
1347 (&[0, 2, 4, 8], 3, (&[0, 2], &[4, 8])),
1348 (&[0, 2, 4, 8], 6, (&[0, 2, 4], &[4, 8])),
1349 ];
1350 for (ranges, pos, (left, right)) in cases {
1351 assert_eq!(split(ranges, pos), (left, right));
1352 }
1353 }
1354
1355 #[test]
1356 fn test_intersects_0() {
1357 let cases: Vec<(&[u64], Range<u64>, bool)> = vec![
1358 (&[0, 2], 0..2, true),
1359 (&[0, 2], 2..4, false),
1360 (&[0, 2, 4, 8], 0..2, true),
1361 (&[0, 2, 4, 8], 2..4, false),
1362 (&[0, 2, 4, 8], 4..8, true),
1363 (&[0, 2, 4, 8], 8..12, false),
1364 ];
1365 for (ranges, range, expected) in cases {
1366 assert_eq!(intersects(ranges, range), expected);
1367 }
1368 }
1369
1370 #[test]
1371 fn contains_0() {
1372 let cases: Vec<(&[u64], u64, bool)> = vec![
1373 (&[0, 2], 0, true),
1374 (&[0, 2], 1, true),
1375 (&[0, 2], 2, false),
1376 (&[0, 2, 4, 8], 3, false),
1377 (&[0, 2, 4, 8], 4, true),
1378 ];
1379 for (ranges, pos, expected) in cases {
1380 assert_eq!(contains(ranges, &pos), expected);
1381 }
1382 }
1383}
1384
1385#[cfg(test)]
1386mod tests {
1387 use super::*;
1388 use num_traits::{Bounded, PrimInt};
1389 use obey::*;
1390 use quickcheck::*;
1391 use std::collections::BTreeSet;
1392 use std::ops::RangeBounds;
1393
1394 impl<T: RangeSetEntry + Clone, A: Array<Item = T>> RangeSet<A> {
1395 fn from_range_bounds<R: RangeBounds<T>>(r: R) -> std::result::Result<Self, ()> {
1396 match (r.start_bound(), r.end_bound()) {
1397 (Bound::Unbounded, Bound::Unbounded) => Ok(Self::all()),
1398 (Bound::Unbounded, Bound::Excluded(b)) => Ok(Self::from_range_until(b.clone())),
1399 (Bound::Included(a), Bound::Unbounded) => Ok(Self::from_range_from(a.clone())),
1400 (Bound::Included(a), Bound::Excluded(b)) => Ok(Self::from_range(Range {
1401 start: a.clone(),
1402 end: b.clone(),
1403 })),
1404 _ => Err(()),
1405 }
1406 }
1407 }
1408
1409 impl<T: Arbitrary + Ord, A: Array<Item = T> + Clone + 'static> Arbitrary for RangeSet<A> {
1410 fn arbitrary<G: Gen>(g: &mut G) -> Self {
1411 let mut boundaries: Vec<T> = Arbitrary::arbitrary(g);
1412 boundaries.truncate(4);
1413 boundaries.sort();
1414 boundaries.dedup();
1415 Self::new_unchecked_impl(boundaries.into())
1416 }
1417 }
1418
1419 impl<E: PrimInt + RangeSetEntry + Clone, A: Array<Item = E>> TestSamples<E, bool> for RangeSet<A> {
1421 fn samples(&self, res: &mut BTreeSet<E>) {
1422 res.insert(<E as Bounded>::min_value());
1423 for x in self.0.iter().cloned() {
1424 res.insert(x.saturating_sub(E::one()));
1425 res.insert(x);
1426 res.insert(x.saturating_add(E::one()));
1427 }
1428 res.insert(E::max_value());
1429 }
1430
1431 fn at(&self, elem: E) -> bool {
1432 self.contains(&elem)
1433 }
1434 }
1435 type Test = RangeSet<[i64; 4]>;
1436
1437 #[test]
1438 fn smoke_test() {
1439 let x: Test = Test::from(0..10);
1440 println!(
1441 "{:?} {:?} {:?} {:?} {:?}",
1442 x,
1443 x.contains(&0),
1444 x.contains(&1),
1445 x.contains(&9),
1446 x.contains(&10)
1447 );
1448
1449 let y: Test = Test::from(..10);
1450 let z: Test = Test::from(20..);
1451
1452 let r: Test = (&x).bitor(&z);
1453
1454 println!("{:?} {:?} {:?} {:?}", x, y, z, r);
1455
1456 let r2: Test = &x & &y;
1457 let r3: Test = &x | &y;
1458 let r4 = y.is_disjoint(&z);
1459 let r5 = (&y).bitand(&z);
1460
1461 println!("{:?}", r2);
1462 println!("{:?}", r3);
1463 println!("{:?} {:?}", r4, r5);
1464 }
1465
1466 #[cfg(feature = "serde")]
1467 #[quickcheck]
1468 fn range_seq_serde(a: Test) -> bool {
1469 let bytes = serde_cbor::to_vec(&a).unwrap();
1470 let b: Test = serde_cbor::from_slice(&bytes).unwrap();
1471 a == b
1472 }
1473
1474 #[cfg(feature = "rkyv")]
1475 #[quickcheck]
1476 fn range_seq_rkyv_unvalidated(a: Test) -> bool {
1477 use rkyv::*;
1478 use ser::Serializer;
1479 let mut serializer = ser::serializers::AllocSerializer::<256>::default();
1480 serializer.serialize_value(&a).unwrap();
1481 let bytes = serializer.into_serializer().into_inner();
1482 let archived = unsafe { rkyv::archived_root::<Test>(&bytes) };
1483 let deserialized: Test = archived.deserialize(&mut Infallible).unwrap();
1484 a == deserialized
1485 }
1486
1487 #[cfg(feature = "rkyv_validated")]
1488 #[quickcheck]
1489 fn range_seq_rkyv_validated(a: Test) -> bool {
1490 use rkyv::*;
1491 use ser::Serializer;
1492 let mut serializer = ser::serializers::AllocSerializer::<256>::default();
1493 serializer.serialize_value(&a).unwrap();
1494 let bytes = serializer.into_serializer().into_inner();
1495 let archived = rkyv::check_archived_root::<Test>(&bytes).unwrap();
1496 let deserialized: Test = archived.deserialize(&mut Infallible).unwrap();
1497 a == deserialized
1498 }
1499
1500 #[cfg(feature = "rkyv_validated")]
1501 #[test]
1502 fn range_seq_rkyv_errors() {
1503 use rkyv::*;
1504 use std::num::NonZeroU64;
1505
1506 let mut bytes = AlignedVec::new();
1508 bytes.extend_from_slice(&hex::decode("000000000000000002000000").unwrap());
1509 assert!(rkyv::check_archived_root::<Test>(&bytes).is_err());
1510
1511 let mut bytes = AlignedVec::new();
1513 bytes.extend_from_slice(
1514 &hex::decode("02000000000000000100000000000000f0ffffff0200000000000000").unwrap(),
1515 );
1516 assert!(rkyv::check_archived_root::<Test>(&bytes).is_err());
1517
1518 let mut bytes = AlignedVec::new();
1520 bytes.extend_from_slice(
1521 &hex::decode("00000000000000000100000000000000f0ffffff0200000000000000").unwrap(),
1522 );
1523 assert!(rkyv::check_archived_root::<RangeSet2<NonZeroU64>>(&bytes).is_err());
1524 }
1525
1526 #[quickcheck]
1527 fn ranges_consistent(a: Test) -> bool {
1528 let mut b = Test::empty();
1529 for e in a.iter() {
1530 let e = e.cloned();
1531 b |= Test::from_range_bounds(e).unwrap();
1532 }
1533 a == b
1534 }
1535
1536 #[quickcheck]
1537 fn is_disjoint_sample(a: Test, b: Test) -> bool {
1538 let res = binary_property_test(&a, &b, a.is_disjoint(&b), |a, b| !(a & b));
1539 if !res {
1540 println!("{:?} {:?} {:?}", a, b, a.is_disjoint(&b));
1541 }
1542 res
1543 }
1544
1545 #[quickcheck]
1546 fn is_subset_sample(a: Test, b: Test) -> bool {
1547 binary_property_test(&a, &b, a.is_subset(&b), |a, b| !a | b)
1548 }
1549
1550 #[quickcheck]
1551 fn negation_check(a: RangeSet2<i64>) -> bool {
1552 unary_element_test(&a, !a.clone(), |x| !x)
1553 }
1554
1555 #[quickcheck]
1556 fn union_check(a: RangeSet2<i64>, b: RangeSet2<i64>) -> bool {
1557 binary_element_test(&a, &b, &a | &b, |a, b| a | b)
1558 }
1559
1560 #[quickcheck]
1561 fn intersection_check(a: RangeSet2<i64>, b: RangeSet2<i64>) -> bool {
1562 binary_element_test(&a, &b, &a & &b, |a, b| a & b)
1563 }
1564
1565 #[quickcheck]
1566 fn xor_check(a: RangeSet2<i64>, b: RangeSet2<i64>) -> bool {
1567 binary_element_test(&a, &b, &a ^ &b, |a, b| a ^ b)
1568 }
1569
1570 #[quickcheck]
1571 fn difference_check(a: RangeSet2<i64>, b: RangeSet2<i64>) -> bool {
1572 binary_element_test(&a, &b, &a - &b, |a, b| a & !b)
1573 }
1574
1575 bitop_assign_consistent!(Test);
1576 bitop_symmetry!(Test);
1577 bitop_empty!(Test);
1578 bitop_sub_not_all!(Test);
1579 set_predicate_consistent!(Test);
1580}