1use crate::world::unsafe_world_cell::UnsafeWorldCell;
2use crate::{component::ComponentId, resource::IS_RESOURCE};
3use alloc::{format, string::String, vec, vec::Vec};
4use core::iter::FusedIterator;
5use core::{fmt, fmt::Debug};
6use derive_more::From;
7use fixedbitset::{Difference, FixedBitSet, Intersection, IntoOnes, Ones, Union};
8use thiserror::Error;
9
10#[derive(Eq, PartialEq, Default, Hash, Debug)]
15pub struct Access {
16 read_and_writes: ComponentIdSet,
19 writes: ComponentIdSet,
22 read_and_writes_inverted: bool,
25 writes_inverted: bool,
28 archetypal: ComponentIdSet,
30}
31
32impl Clone for Access {
34 fn clone(&self) -> Self {
35 Self {
36 read_and_writes: self.read_and_writes.clone(),
37 writes: self.writes.clone(),
38 read_and_writes_inverted: self.read_and_writes_inverted,
39 writes_inverted: self.writes_inverted,
40 archetypal: self.archetypal.clone(),
41 }
42 }
43
44 fn clone_from(&mut self, source: &Self) {
45 self.read_and_writes.clone_from(&source.read_and_writes);
46 self.writes.clone_from(&source.writes);
47 self.read_and_writes_inverted = source.read_and_writes_inverted;
48 self.writes_inverted = source.writes_inverted;
49 self.archetypal.clone_from(&source.archetypal);
50 }
51}
52
53impl Access {
54 pub const fn new() -> Self {
56 Self {
57 read_and_writes_inverted: false,
58 writes_inverted: false,
59 read_and_writes: ComponentIdSet::new(),
60 writes: ComponentIdSet::new(),
61 archetypal: ComponentIdSet::new(),
62 }
63 }
64
65 pub(crate) const fn new_read_all() -> Self {
69 let mut access = Self::new();
70 access.read_and_writes_inverted = true;
73 access
74 }
75
76 pub(crate) const fn new_write_all() -> Self {
80 let mut access = Self::new();
81 access.read_and_writes_inverted = true;
84 access.writes_inverted = true;
85 access
86 }
87
88 #[deprecated(since = "0.19.0", note = "use Access::add_read")]
90 pub fn add_component_read(&mut self, index: ComponentId) {
91 self.add_read(index);
92 }
93
94 pub fn add_read(&mut self, index: ComponentId) {
96 if !self.read_and_writes_inverted {
97 self.read_and_writes.insert(index);
98 } else {
99 self.read_and_writes.remove(index);
100 }
101 }
102
103 #[deprecated(since = "0.19.0", note = "use Access::add_write")]
105 pub fn add_component_write(&mut self, index: ComponentId) {
106 self.add_write(index);
107 }
108
109 pub fn add_write(&mut self, index: ComponentId) {
111 self.add_read(index);
112 if !self.writes_inverted {
113 self.writes.insert(index);
114 } else {
115 self.writes.remove(index);
116 }
117 }
118
119 #[deprecated(
121 since = "0.19.0",
122 note = "Call `FilteredAccessSet::add_resource_read`. If this is called in a `WorldQuery` impl, then you will need to implement `init_nested_access` to modify the `FilteredAccessSet`."
123 )]
124 pub fn add_resource_read(&mut self, index: ComponentId) {
125 self.add_read(index);
126 }
127
128 #[deprecated(
130 since = "0.19.0",
131 note = "Call `FilteredAccessSet::add_resource_write`. If this is called in a `WorldQuery` impl, then you will need to implement `init_nested_access` to modify the `FilteredAccessSet`."
132 )]
133 pub fn add_resource_write(&mut self, index: ComponentId) {
134 self.add_write(index);
135 }
136
137 #[deprecated(since = "0.19.0", note = "use Access::remove_read")]
139 pub fn remove_component_read(&mut self, index: ComponentId) {
140 self.remove_read(index);
141 }
142
143 pub fn remove_read(&mut self, index: ComponentId) {
152 self.remove_write(index);
153 if self.read_and_writes_inverted {
154 self.read_and_writes.insert(index);
155 } else {
156 self.read_and_writes.remove(index);
157 }
158 }
159
160 #[deprecated(since = "0.19.0", note = "use Access::remove_write")]
162 pub fn remove_component_write(&mut self, index: ComponentId) {
163 self.remove_write(index);
164 }
165
166 pub fn remove_write(&mut self, index: ComponentId) {
175 if self.writes_inverted {
176 self.writes.insert(index);
177 } else {
178 self.writes.remove(index);
179 }
180 }
181
182 pub fn add_archetypal(&mut self, index: ComponentId) {
192 self.archetypal.insert(index);
193 }
194
195 #[deprecated(since = "0.19.0", note = "use Access::has_read")]
197 pub fn has_component_read(&self, index: ComponentId) -> bool {
198 self.has_read(index)
199 }
200
201 pub fn has_read(&self, index: ComponentId) -> bool {
203 self.read_and_writes_inverted ^ self.read_and_writes.contains(index)
204 }
205
206 #[deprecated(since = "0.19.0", note = "use Access::has_any_read")]
208 pub fn has_any_component_read(&self) -> bool {
209 self.has_any_read()
210 }
211
212 pub fn has_any_read(&self) -> bool {
214 self.read_and_writes_inverted || !self.read_and_writes.is_clear()
215 }
216
217 #[deprecated(since = "0.19.0", note = "use Access::has_write")]
219 pub fn has_component_write(&self, index: ComponentId) -> bool {
220 self.has_write(index)
221 }
222
223 pub fn has_write(&self, index: ComponentId) -> bool {
225 self.writes_inverted ^ self.writes.contains(index)
226 }
227
228 #[deprecated(since = "0.19.0", note = "use Access::has_any_write")]
230 pub fn has_any_component_write(&self) -> bool {
231 self.has_any_write()
232 }
233
234 pub fn has_any_write(&self) -> bool {
236 self.writes_inverted || !self.writes.is_clear()
237 }
238
239 #[deprecated(since = "0.19.0", note = "use Access::has_read")]
241 pub fn has_resource_read(&self, index: ComponentId) -> bool {
242 self.has_read(index)
243 }
244
245 #[deprecated(since = "0.19.0", note = "use Access::has_any_read")]
247 pub fn has_any_resource_read(&self) -> bool {
248 self.has_any_read()
249 }
250
251 #[deprecated(since = "0.19.0", note = "use Access::has_write")]
253 pub fn has_resource_write(&self, index: ComponentId) -> bool {
254 self.has_write(index)
255 }
256
257 #[deprecated(since = "0.19.0", note = "use Access::has_any_write")]
259 pub fn has_any_resource_write(&self) -> bool {
260 self.has_any_write()
261 }
262
263 pub fn has_archetypal(&self, index: ComponentId) -> bool {
272 self.archetypal.contains(index)
273 }
274
275 #[deprecated(since = "0.19.0", note = "use Access::read_all")]
277 pub fn read_all_components(&mut self) {
278 self.read_all();
279 }
280
281 #[inline]
283 pub fn read_all(&mut self) {
284 self.read_and_writes_inverted = true;
285 self.read_and_writes.clear();
286 }
287
288 #[deprecated(since = "0.19.0", note = "use Access::write_all")]
290 pub fn write_all_components(&mut self) {
291 self.write_all();
292 }
293
294 #[inline]
296 pub fn write_all(&mut self) {
297 self.read_all();
298 self.writes_inverted = true;
299 self.writes.clear();
300 }
301
302 #[deprecated(since = "0.19.0", note = "use Access::has_read_all")]
304 pub fn has_read_all_components(&self) -> bool {
305 self.has_read_all()
306 }
307
308 #[inline]
310 pub fn has_read_all(&self) -> bool {
311 self.read_and_writes_inverted && self.read_and_writes.is_clear()
312 }
313
314 #[deprecated(since = "0.19.0", note = "use Access::has_write_all")]
316 pub fn has_write_all_components(&self) -> bool {
317 self.has_write_all()
318 }
319
320 #[inline]
322 pub fn has_write_all(&self) -> bool {
323 self.writes_inverted && self.writes.is_clear()
324 }
325
326 pub fn clear_writes(&mut self) {
328 self.writes_inverted = false;
329 self.writes.clear();
330 }
331
332 pub fn clear(&mut self) {
334 self.read_and_writes_inverted = false;
335 self.writes_inverted = false;
336 self.read_and_writes.clear();
337 self.writes.clear();
338 }
339
340 pub fn extend(&mut self, other: &Access) {
342 invertible_union_with(
343 &mut self.read_and_writes,
344 &mut self.read_and_writes_inverted,
345 &other.read_and_writes,
346 other.read_and_writes_inverted,
347 );
348 invertible_union_with(
349 &mut self.writes,
350 &mut self.writes_inverted,
351 &other.writes,
352 other.writes_inverted,
353 );
354 self.archetypal.union_with(&other.archetypal);
355 }
356
357 pub fn remove_conflicting_access(&mut self, other: &Access) {
361 invertible_difference_with(
362 &mut self.read_and_writes,
363 &mut self.read_and_writes_inverted,
364 &other.writes,
365 other.writes_inverted,
366 );
367 invertible_difference_with(
368 &mut self.writes,
369 &mut self.writes_inverted,
370 &other.read_and_writes,
371 other.read_and_writes_inverted,
372 );
373 }
374
375 #[deprecated(since = "0.19.0", note = "use Access::is_compatible")]
377 pub fn is_components_compatible(&self, other: &Access) -> bool {
378 self.is_compatible(other)
379 }
380
381 pub fn is_compatible(&self, other: &Access) -> bool {
386 for (
389 lhs_writes,
390 rhs_reads_and_writes,
391 lhs_writes_inverted,
392 rhs_reads_and_writes_inverted,
393 ) in [
394 (
395 &self.writes,
396 &other.read_and_writes,
397 self.writes_inverted,
398 other.read_and_writes_inverted,
399 ),
400 (
401 &other.writes,
402 &self.read_and_writes,
403 other.writes_inverted,
404 self.read_and_writes_inverted,
405 ),
406 ] {
407 match (lhs_writes_inverted, rhs_reads_and_writes_inverted) {
408 (true, true) => return false,
409 (false, true) => {
410 if !lhs_writes.is_subset(rhs_reads_and_writes) {
411 return false;
412 }
413 }
414 (true, false) => {
415 if !rhs_reads_and_writes.is_subset(lhs_writes) {
416 return false;
417 }
418 }
419 (false, false) => {
420 if !lhs_writes.is_disjoint(rhs_reads_and_writes) {
421 return false;
422 }
423 }
424 }
425 }
426
427 true
428 }
429
430 #[deprecated(since = "0.19.0", note = "use Access::is_subset")]
433 pub fn is_subset_components(&self, other: &Access) -> bool {
434 self.is_subset(other)
435 }
436
437 pub fn is_subset(&self, other: &Access) -> bool {
440 for (
441 our_components,
442 their_components,
443 our_components_inverted,
444 their_components_inverted,
445 ) in [
446 (
447 &self.read_and_writes,
448 &other.read_and_writes,
449 self.read_and_writes_inverted,
450 other.read_and_writes_inverted,
451 ),
452 (
453 &self.writes,
454 &other.writes,
455 self.writes_inverted,
456 other.writes_inverted,
457 ),
458 ] {
459 match (our_components_inverted, their_components_inverted) {
460 (true, true) => {
461 if !their_components.is_subset(our_components) {
462 return false;
463 }
464 }
465 (true, false) => {
466 return false;
467 }
468 (false, true) => {
469 if !our_components.is_disjoint(their_components) {
470 return false;
471 }
472 }
473 (false, false) => {
474 if !our_components.is_subset(their_components) {
475 return false;
476 }
477 }
478 }
479 }
480
481 true
482 }
483
484 #[inline]
486 pub fn get_conflicts(&self, other: &Access) -> AccessConflicts {
487 let mut conflicts = ComponentIdSet::new();
488
489 for (
492 lhs_writes,
493 rhs_reads_and_writes,
494 lhs_writes_inverted,
495 rhs_reads_and_writes_inverted,
496 ) in [
497 (
498 &self.writes,
499 &other.read_and_writes,
500 self.writes_inverted,
501 other.read_and_writes_inverted,
502 ),
503 (
504 &other.writes,
505 &self.read_and_writes,
506 other.writes_inverted,
507 self.read_and_writes_inverted,
508 ),
509 ] {
510 let temp_conflicts: ComponentIdSet =
513 match (lhs_writes_inverted, rhs_reads_and_writes_inverted) {
514 (true, true) => return AccessConflicts::All,
515 (false, true) => lhs_writes.difference(rhs_reads_and_writes).collect(),
516 (true, false) => rhs_reads_and_writes.difference(lhs_writes).collect(),
517 (false, false) => lhs_writes.intersection(rhs_reads_and_writes).collect(),
518 };
519 conflicts.union_with(&temp_conflicts);
520 }
521
522 AccessConflicts::Individual(conflicts)
523 }
524
525 pub fn archetypal(&self) -> &ComponentIdSet {
534 &self.archetypal
535 }
536
537 pub fn try_reads_and_writes(&self) -> Result<&ComponentIdSet, UnboundedAccessError> {
540 if self.read_and_writes_inverted {
543 return Err(UnboundedAccessError {
544 writes_inverted: self.writes_inverted,
545 read_and_writes_inverted: self.read_and_writes_inverted,
546 });
547 }
548 Ok(&self.read_and_writes)
549 }
550
551 pub fn try_writes(&self) -> Result<&ComponentIdSet, UnboundedAccessError> {
554 if self.writes_inverted {
555 return Err(UnboundedAccessError {
556 writes_inverted: self.writes_inverted,
557 read_and_writes_inverted: self.read_and_writes_inverted,
558 });
559 }
560 Ok(&self.writes)
561 }
562
563 #[deprecated(since = "0.19.0", note = "use Access::try_iter_access")]
565 pub fn try_iter_component_access(
566 &self,
567 ) -> Result<impl Iterator<Item = ComponentAccessKind> + '_, UnboundedAccessError> {
568 self.try_iter_access()
569 }
570
571 pub fn try_iter_access(
602 &self,
603 ) -> Result<impl Iterator<Item = ComponentAccessKind> + '_, UnboundedAccessError> {
604 let reads_and_writes = self.try_reads_and_writes()?.iter().map(|index| {
605 if self.writes.contains(index) {
606 ComponentAccessKind::Exclusive(index)
607 } else {
608 ComponentAccessKind::Shared(index)
609 }
610 });
611
612 let archetypal = self
613 .archetypal
614 .difference(&self.read_and_writes)
615 .map(ComponentAccessKind::Archetypal);
616
617 Ok(reads_and_writes.chain(archetypal))
618 }
619}
620
621fn invertible_union_with(
630 self_set: &mut ComponentIdSet,
631 self_inverted: &mut bool,
632 other_set: &ComponentIdSet,
633 other_inverted: bool,
634) {
635 match (*self_inverted, other_inverted) {
636 (true, true) => self_set.intersect_with(other_set),
637 (true, false) => self_set.difference_with(other_set),
638 (false, true) => {
639 *self_inverted = true;
640 self_set.difference_from(other_set);
641 }
642 (false, false) => self_set.union_with(other_set),
643 }
644}
645
646fn invertible_difference_with(
655 self_set: &mut ComponentIdSet,
656 self_inverted: &mut bool,
657 other_set: &ComponentIdSet,
658 other_inverted: bool,
659) {
660 *self_inverted = !*self_inverted;
663 invertible_union_with(self_set, self_inverted, other_set, other_inverted);
664 *self_inverted = !*self_inverted;
665}
666
667#[derive(Clone, Copy, PartialEq, Eq, Debug, Error)]
670#[error("Access is unbounded")]
671pub struct UnboundedAccessError {
672 pub writes_inverted: bool,
675 pub read_and_writes_inverted: bool,
678}
679
680#[derive(PartialEq, Eq, Hash, Debug, Clone, Copy)]
682pub enum ComponentAccessKind {
683 Archetypal(ComponentId),
685 Shared(ComponentId),
687 Exclusive(ComponentId),
689}
690
691impl ComponentAccessKind {
692 pub fn index(&self) -> &ComponentId {
694 let (Self::Archetypal(value) | Self::Shared(value) | Self::Exclusive(value)) = self;
695 value
696 }
697}
698
699#[derive(Debug, Eq, PartialEq)]
720pub struct FilteredAccess {
721 pub(crate) access: Access,
722 pub(crate) required: ComponentIdSet,
723 pub(crate) filter_sets: Vec<AccessFilters>,
726}
727
728impl Clone for FilteredAccess {
730 fn clone(&self) -> Self {
731 Self {
732 access: self.access.clone(),
733 required: self.required.clone(),
734 filter_sets: self.filter_sets.clone(),
735 }
736 }
737
738 fn clone_from(&mut self, source: &Self) {
739 self.access.clone_from(&source.access);
740 self.required.clone_from(&source.required);
741 self.filter_sets.clone_from(&source.filter_sets);
742 }
743}
744
745impl Default for FilteredAccess {
746 fn default() -> Self {
747 Self::matches_everything()
748 }
749}
750
751impl From<FilteredAccess> for FilteredAccessSet {
752 fn from(filtered_access: FilteredAccess) -> Self {
753 let mut base = FilteredAccessSet::default();
754 base.add(filtered_access);
755 base
756 }
757}
758
759#[derive(Debug, PartialEq, From)]
761pub enum AccessConflicts {
762 All,
764 Individual(ComponentIdSet),
766}
767
768impl AccessConflicts {
769 fn add(&mut self, other: &Self) {
770 match (self, other) {
771 (s, AccessConflicts::All) => {
772 *s = AccessConflicts::All;
773 }
774 (AccessConflicts::Individual(this), AccessConflicts::Individual(other)) => {
775 this.extend(other);
776 }
777 _ => {}
778 }
779 }
780
781 pub fn is_empty(&self) -> bool {
783 match self {
784 Self::All => false,
785 Self::Individual(set) => set.is_clear(),
786 }
787 }
788
789 pub(crate) fn format_conflict_list(&self, world: UnsafeWorldCell) -> String {
790 match self {
791 AccessConflicts::All => String::new(),
792 AccessConflicts::Individual(indices) => indices
793 .iter()
794 .map(|index| {
795 format!(
796 "{}",
797 world.components().get_name(index).unwrap().shortname()
798 )
799 })
800 .collect::<Vec<_>>()
801 .join(", "),
802 }
803 }
804
805 pub(crate) fn empty() -> Self {
807 Self::Individual(ComponentIdSet::new())
808 }
809}
810
811impl From<Vec<ComponentId>> for AccessConflicts {
812 fn from(value: Vec<ComponentId>) -> Self {
813 Self::Individual(value.into_iter().collect())
814 }
815}
816
817impl FilteredAccess {
818 pub fn matches_everything() -> Self {
821 Self {
822 access: Access::default(),
823 required: ComponentIdSet::default(),
824 filter_sets: vec![AccessFilters::default()],
825 }
826 }
827
828 pub fn matches_nothing() -> Self {
831 Self {
832 access: Access::default(),
833 required: ComponentIdSet::default(),
834 filter_sets: Vec::new(),
835 }
836 }
837
838 #[inline]
840 pub fn access(&self) -> &Access {
841 &self.access
842 }
843
844 #[inline]
846 pub fn access_mut(&mut self) -> &mut Access {
847 &mut self.access
848 }
849
850 #[deprecated(since = "0.19.0", note = "use FilteredAccess::add_read")]
852 pub fn add_component_read(&mut self, index: ComponentId) {
853 self.add_read(index);
854 }
855
856 pub fn add_read(&mut self, index: ComponentId) {
858 self.access.add_read(index);
859 self.add_required(index);
860 self.and_with(index);
861 }
862
863 #[deprecated(since = "0.19.0", note = "use FilteredAccess::add_write")]
865 pub fn add_component_write(&mut self, index: ComponentId) {
866 self.add_write(index);
867 }
868
869 pub fn add_write(&mut self, index: ComponentId) {
871 self.access.add_write(index);
872 self.add_required(index);
873 self.and_with(index);
874 }
875
876 fn add_required(&mut self, index: ComponentId) {
877 self.required.insert(index);
878 }
879
880 pub fn and_with(&mut self, index: ComponentId) {
885 for filter in &mut self.filter_sets {
886 filter.with.insert(index);
887 }
888 }
889
890 pub fn and_without(&mut self, index: ComponentId) {
895 for filter in &mut self.filter_sets {
896 filter.without.insert(index);
897 }
898 }
899
900 pub fn append_or(&mut self, other: &FilteredAccess) {
906 self.filter_sets.append(&mut other.filter_sets.clone());
907 }
908
909 pub fn extend_access(&mut self, other: &FilteredAccess) {
911 self.access.extend(&other.access);
912 }
913
914 pub fn is_compatible(&self, other: &FilteredAccess) -> bool {
916 if self.access.is_compatible(&other.access) {
917 return true;
918 }
919
920 self.filter_sets.iter().all(|filter| {
928 other
929 .filter_sets
930 .iter()
931 .all(|other_filter| filter.is_ruled_out_by(other_filter))
932 })
933 }
934
935 pub fn get_conflicts(&self, other: &FilteredAccess) -> AccessConflicts {
937 if !self.is_compatible(other) {
938 return self.access.get_conflicts(&other.access);
940 }
941 AccessConflicts::empty()
942 }
943
944 pub fn extend(&mut self, other: &FilteredAccess) {
951 self.access.extend(&other.access);
952 self.required.union_with(&other.required);
953
954 if other.filter_sets.len() == 1 {
957 for filter in &mut self.filter_sets {
958 filter.with.union_with(&other.filter_sets[0].with);
959 filter.without.union_with(&other.filter_sets[0].without);
960 }
961 return;
962 }
963
964 let mut new_filters = Vec::with_capacity(self.filter_sets.len() * other.filter_sets.len());
965 for filter in &self.filter_sets {
966 for other_filter in &other.filter_sets {
967 let mut new_filter = filter.clone();
968 new_filter.with.union_with(&other_filter.with);
969 new_filter.without.union_with(&other_filter.without);
970 new_filters.push(new_filter);
971 }
972 }
973 self.filter_sets = new_filters;
974 }
975
976 pub fn read_all(&mut self) {
978 self.access.read_all();
979 }
980
981 pub fn write_all(&mut self) {
983 self.access.write_all();
984 }
985
986 #[deprecated(since = "0.19.0", note = "use FilteredAccess::read_all")]
988 pub fn read_all_components(&mut self) {
989 self.read_all();
990 }
991
992 #[deprecated(since = "0.19.0", note = "use FilteredAccess::write_all")]
994 pub fn write_all_components(&mut self) {
995 self.write_all();
996 }
997
998 pub fn is_subset(&self, other: &FilteredAccess) -> bool {
1001 self.required.is_subset(&other.required) && self.access().is_subset(other.access())
1002 }
1003
1004 pub fn required(&self) -> &ComponentIdSet {
1014 &self.required
1015 }
1016
1017 pub fn filter_sets(&self) -> &[AccessFilters] {
1022 &self.filter_sets
1023 }
1024
1025 pub fn with_filters(&self) -> impl Iterator<Item = ComponentId> + '_ {
1027 self.filter_sets.iter().flat_map(|f| f.with.iter())
1028 }
1029
1030 pub fn without_filters(&self) -> impl Iterator<Item = ComponentId> + '_ {
1032 self.filter_sets.iter().flat_map(|f| f.without.iter())
1033 }
1034
1035 pub fn contains(&self, index: ComponentId) -> bool {
1039 self.access().has_archetypal(index)
1040 || self
1041 .filter_sets
1042 .iter()
1043 .any(|f| f.with.contains(index) || f.without.contains(index))
1044 }
1045}
1046
1047#[derive(Eq, PartialEq, Default, Debug)]
1051pub struct AccessFilters {
1052 pub(crate) with: ComponentIdSet,
1053 pub(crate) without: ComponentIdSet,
1054}
1055
1056impl Clone for AccessFilters {
1058 fn clone(&self) -> Self {
1059 Self {
1060 with: self.with.clone(),
1061 without: self.without.clone(),
1062 }
1063 }
1064
1065 fn clone_from(&mut self, source: &Self) {
1066 self.with.clone_from(&source.with);
1067 self.without.clone_from(&source.without);
1068 }
1069}
1070
1071impl AccessFilters {
1072 pub fn with(&self) -> &ComponentIdSet {
1074 &self.with
1075 }
1076
1077 pub fn without(&self) -> &ComponentIdSet {
1079 &self.without
1080 }
1081
1082 fn is_ruled_out_by(&self, other: &Self) -> bool {
1083 !self.with.is_disjoint(&other.without) || !self.without.is_disjoint(&other.with)
1089 }
1090}
1091
1092#[derive(Debug, PartialEq, Eq, Default)]
1100pub struct FilteredAccessSet {
1101 combined_access: Access,
1102 filtered_accesses: Vec<FilteredAccess>,
1103}
1104
1105impl Clone for FilteredAccessSet {
1107 fn clone(&self) -> Self {
1108 Self {
1109 combined_access: self.combined_access.clone(),
1110 filtered_accesses: self.filtered_accesses.clone(),
1111 }
1112 }
1113
1114 fn clone_from(&mut self, source: &Self) {
1115 self.combined_access.clone_from(&source.combined_access);
1116 self.filtered_accesses.clone_from(&source.filtered_accesses);
1117 }
1118}
1119
1120impl FilteredAccessSet {
1121 pub const fn new() -> Self {
1123 Self {
1124 combined_access: Access::new(),
1125 filtered_accesses: Vec::new(),
1126 }
1127 }
1128
1129 #[inline]
1131 pub fn combined_access(&self) -> &Access {
1132 &self.combined_access
1133 }
1134
1135 #[inline]
1137 pub fn filtered_accesses(&self) -> &[FilteredAccess] {
1138 &self.filtered_accesses
1139 }
1140
1141 pub fn is_compatible(&self, other: &FilteredAccessSet) -> bool {
1154 if self.combined_access.is_compatible(other.combined_access()) {
1155 return true;
1156 }
1157 for filtered in &self.filtered_accesses {
1158 for other_filtered in &other.filtered_accesses {
1159 if !filtered.is_compatible(other_filtered) {
1160 return false;
1161 }
1162 }
1163 }
1164 true
1165 }
1166
1167 pub fn get_conflicts(&self, other: &FilteredAccessSet) -> AccessConflicts {
1169 let mut conflicts = AccessConflicts::empty();
1171 if !self.combined_access.is_compatible(other.combined_access()) {
1172 for filtered in &self.filtered_accesses {
1173 for other_filtered in &other.filtered_accesses {
1174 conflicts.add(&filtered.get_conflicts(other_filtered));
1175 }
1176 }
1177 }
1178 conflicts
1179 }
1180
1181 pub fn get_conflicts_single(&self, filtered_access: &FilteredAccess) -> AccessConflicts {
1183 let mut conflicts = AccessConflicts::empty();
1185 if !self.combined_access.is_compatible(filtered_access.access()) {
1186 for filtered in &self.filtered_accesses {
1187 conflicts.add(&filtered.get_conflicts(filtered_access));
1188 }
1189 }
1190 conflicts
1191 }
1192
1193 pub fn add(&mut self, filtered_access: FilteredAccess) {
1195 self.combined_access.extend(&filtered_access.access);
1196 self.filtered_accesses.push(filtered_access);
1197 }
1198
1199 #[deprecated(since = "0.19.0", note = "FilteredAccessSet::add_resource_read")]
1201 pub fn add_unfiltered_resource_read(&mut self, index: ComponentId) {
1202 self.add_resource_read(index);
1203 }
1204
1205 pub fn add_resource_read(&mut self, index: ComponentId) {
1207 let mut filter = FilteredAccess::default();
1208 filter.add_read(index);
1209 filter.and_with(IS_RESOURCE);
1210 self.add(filter);
1211 }
1212
1213 pub(crate) fn add_unfiltered_component_read(&mut self, index: ComponentId) {
1215 let mut filter = FilteredAccess::default();
1216 filter.add_read(index);
1217 self.add(filter);
1218 }
1219
1220 pub fn add_unfiltered_read_all_components(&mut self) {
1222 let mut filter = FilteredAccess::default();
1223 filter.access.read_all();
1224 self.add(filter);
1225 }
1226
1227 #[deprecated(since = "0.19.0", note = "FilteredAccessSet::add_resource_write")]
1229 pub fn add_unfiltered_resource_write(&mut self, index: ComponentId) {
1230 self.add_resource_write(index);
1231 }
1232
1233 pub fn add_resource_write(&mut self, index: ComponentId) {
1235 let mut filter = FilteredAccess::default();
1236 filter.add_write(index);
1237 filter.and_with(IS_RESOURCE);
1238 self.add(filter);
1239 }
1240
1241 pub(crate) fn add_unfiltered_component_write(&mut self, index: ComponentId) {
1243 let mut filter = FilteredAccess::default();
1244 filter.add_write(index);
1245 self.add(filter);
1246 }
1247
1248 pub fn add_unfiltered_write_all_components(&mut self) {
1250 let mut filter = FilteredAccess::default();
1251 filter.write_all();
1252 self.add(filter);
1253 }
1254
1255 pub fn extend(&mut self, filtered_access_set: FilteredAccessSet) {
1257 self.combined_access
1258 .extend(&filtered_access_set.combined_access);
1259 self.filtered_accesses
1260 .extend(filtered_access_set.filtered_accesses);
1261 }
1262
1263 pub fn read_all(&mut self) {
1265 let mut filter = FilteredAccess::matches_everything();
1266 filter.read_all();
1267 self.add(filter);
1268 }
1269
1270 pub fn write_all(&mut self) {
1272 let mut filter = FilteredAccess::matches_everything();
1273 filter.write_all();
1274 self.add(filter);
1275 }
1276
1277 pub fn clear(&mut self) {
1279 self.combined_access.clear();
1280 self.filtered_accesses.clear();
1281 }
1282}
1283
1284#[derive(Default, Eq, PartialEq, Hash)]
1286#[repr(transparent)]
1287pub struct ComponentIdSet(FixedBitSet);
1288
1289impl ComponentIdSet {
1290 #[inline]
1292 pub const fn new() -> Self {
1293 Self(FixedBitSet::new())
1294 }
1295
1296 #[cfg(test)]
1297 pub(crate) fn from_bits(bits: FixedBitSet) -> Self {
1298 Self(bits)
1299 }
1300
1301 #[inline]
1303 pub fn insert(&mut self, index: ComponentId) {
1304 self.0.grow_and_insert(index.index());
1305 }
1306
1307 #[inline]
1309 pub fn remove(&mut self, index: ComponentId) {
1310 if index.index() < self.0.len() {
1311 self.0.remove(index.index());
1312 }
1313 }
1314
1315 #[inline]
1317 pub fn clear(&mut self) {
1318 self.0.clear();
1319 }
1320
1321 #[inline]
1323 pub fn contains(&self, index: ComponentId) -> bool {
1324 self.0.contains(index.index())
1325 }
1326
1327 #[inline]
1330 pub fn is_disjoint(&self, other: &ComponentIdSet) -> bool {
1331 self.0.is_disjoint(&other.0)
1332 }
1333
1334 #[inline]
1337 pub fn is_subset(&self, other: &ComponentIdSet) -> bool {
1338 self.0.is_subset(&other.0)
1339 }
1340
1341 #[inline]
1343 pub fn is_clear(&self) -> bool {
1344 self.0.is_clear()
1345 }
1346
1347 #[inline]
1349 pub fn iter(&self) -> ComponentIdIter<Ones<'_>> {
1350 ComponentIdIter(self.0.ones())
1351 }
1352
1353 #[inline]
1355 pub fn union<'a>(&'a self, other: &'a ComponentIdSet) -> ComponentIdIter<Union<'a>> {
1356 ComponentIdIter(self.0.union(&other.0))
1357 }
1358
1359 #[inline]
1361 pub fn intersection<'a>(
1362 &'a self,
1363 other: &'a ComponentIdSet,
1364 ) -> ComponentIdIter<Intersection<'a>> {
1365 ComponentIdIter(self.0.intersection(&other.0))
1366 }
1367
1368 #[inline]
1370 pub fn difference<'a>(&'a self, other: &'a ComponentIdSet) -> ComponentIdIter<Difference<'a>> {
1371 ComponentIdIter(self.0.difference(&other.0))
1372 }
1373
1374 #[inline]
1376 pub fn union_with(&mut self, other: &ComponentIdSet) {
1377 self.0.union_with(&other.0);
1378 }
1379
1380 #[inline]
1382 pub fn intersect_with(&mut self, other: &ComponentIdSet) {
1383 self.0.intersect_with(&other.0);
1384 }
1385
1386 #[inline]
1388 pub fn difference_with(&mut self, other: &ComponentIdSet) {
1389 self.0.difference_with(&other.0);
1390 }
1391
1392 #[inline]
1395 pub fn difference_from(&mut self, other: &ComponentIdSet) {
1396 self.0.grow(other.0.len());
1399 self.0.toggle_range(..);
1400 self.0.intersect_with(&other.0);
1401 }
1402}
1403
1404impl Debug for ComponentIdSet {
1405 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1406 f.debug_list().entries(self.0.ones()).finish()
1413 }
1414}
1415
1416impl Clone for ComponentIdSet {
1417 #[inline]
1418 fn clone(&self) -> Self {
1419 Self(self.0.clone())
1420 }
1421
1422 #[inline]
1423 fn clone_from(&mut self, source: &Self) {
1424 self.0.clone_from(&source.0);
1425 }
1426}
1427
1428impl IntoIterator for ComponentIdSet {
1429 type Item = ComponentId;
1430
1431 type IntoIter = ComponentIdIter<IntoOnes>;
1432
1433 #[inline]
1434 fn into_iter(self) -> Self::IntoIter {
1435 ComponentIdIter(self.0.into_ones())
1436 }
1437}
1438
1439impl<'a> IntoIterator for &'a ComponentIdSet {
1440 type Item = ComponentId;
1441
1442 type IntoIter = ComponentIdIter<Ones<'a>>;
1443
1444 #[inline]
1445 fn into_iter(self) -> Self::IntoIter {
1446 self.iter()
1447 }
1448}
1449
1450impl FromIterator<ComponentId> for ComponentIdSet {
1451 #[inline]
1452 fn from_iter<T: IntoIterator<Item = ComponentId>>(iter: T) -> Self {
1453 Self(FixedBitSet::from_iter(
1454 iter.into_iter().map(ComponentId::index),
1455 ))
1456 }
1457}
1458
1459impl Extend<ComponentId> for ComponentIdSet {
1460 #[inline]
1461 fn extend<T: IntoIterator<Item = ComponentId>>(&mut self, iter: T) {
1462 self.0.extend(iter.into_iter().map(ComponentId::index));
1463 }
1464}
1465
1466#[repr(transparent)]
1471pub struct ComponentIdIter<I>(I);
1472
1473impl<I: Iterator<Item = usize>> Iterator for ComponentIdIter<I> {
1474 type Item = ComponentId;
1475
1476 #[inline]
1477 fn next(&mut self) -> Option<Self::Item> {
1478 self.0.next().map(ComponentId::new)
1479 }
1480
1481 #[inline]
1482 fn size_hint(&self) -> (usize, Option<usize>) {
1483 self.0.size_hint()
1484 }
1485}
1486
1487impl<I: DoubleEndedIterator<Item = usize>> DoubleEndedIterator for ComponentIdIter<I> {
1488 #[inline]
1489 fn next_back(&mut self) -> Option<Self::Item> {
1490 self.0.next_back().map(ComponentId::new)
1491 }
1492}
1493
1494impl<I: FusedIterator<Item = usize>> FusedIterator for ComponentIdIter<I> {}
1495
1496#[cfg(test)]
1497mod tests {
1498 use super::{invertible_difference_with, invertible_union_with};
1499 use crate::{
1500 component::ComponentId,
1501 query::{
1502 access::AccessFilters, Access, AccessConflicts, ComponentAccessKind, ComponentIdSet,
1503 FilteredAccess, FilteredAccessSet, UnboundedAccessError,
1504 },
1505 };
1506 use alloc::{vec, vec::Vec};
1507 use fixedbitset::FixedBitSet;
1508
1509 fn create_sample_access() -> Access {
1510 let mut access = Access::default();
1511
1512 access.add_read(ComponentId::new(1));
1513 access.add_read(ComponentId::new(2));
1514 access.add_write(ComponentId::new(3));
1515 access.add_archetypal(ComponentId::new(5));
1516 access.read_all();
1517
1518 access
1519 }
1520
1521 fn create_sample_filtered_access() -> FilteredAccess {
1522 let mut filtered_access = FilteredAccess::default();
1523
1524 filtered_access.add_write(ComponentId::new(1));
1525 filtered_access.add_read(ComponentId::new(2));
1526 filtered_access.add_required(ComponentId::new(3));
1527 filtered_access.and_with(ComponentId::new(4));
1528
1529 filtered_access
1530 }
1531
1532 fn create_sample_access_filters() -> AccessFilters {
1533 let mut access_filters = AccessFilters::default();
1534
1535 access_filters.with.insert(ComponentId::new(3));
1536 access_filters.without.insert(ComponentId::new(5));
1537
1538 access_filters
1539 }
1540
1541 fn create_sample_filtered_access_set() -> FilteredAccessSet {
1542 let mut filtered_access_set = FilteredAccessSet::default();
1543
1544 filtered_access_set.add_unfiltered_component_read(ComponentId::new(2));
1545 filtered_access_set.add_unfiltered_component_write(ComponentId::new(4));
1546 filtered_access_set.read_all();
1547
1548 filtered_access_set
1549 }
1550
1551 #[test]
1552 fn test_access_clone() {
1553 let original = create_sample_access();
1554 let cloned = original.clone();
1555
1556 assert_eq!(original, cloned);
1557 }
1558
1559 #[test]
1560 fn test_access_clone_from() {
1561 let original = create_sample_access();
1562 let mut cloned = Access::default();
1563
1564 cloned.add_write(ComponentId::new(7));
1565 cloned.add_read(ComponentId::new(4));
1566 cloned.add_archetypal(ComponentId::new(8));
1567 cloned.write_all();
1568
1569 cloned.clone_from(&original);
1570
1571 assert_eq!(original, cloned);
1572 }
1573
1574 #[test]
1575 fn test_filtered_access_clone() {
1576 let original = create_sample_filtered_access();
1577 let cloned = original.clone();
1578
1579 assert_eq!(original, cloned);
1580 }
1581
1582 #[test]
1583 fn test_filtered_access_clone_from() {
1584 let original = create_sample_filtered_access();
1585 let mut cloned = FilteredAccess::default();
1586
1587 cloned.add_write(ComponentId::new(7));
1588 cloned.add_read(ComponentId::new(4));
1589 cloned.append_or(&FilteredAccess::default());
1590
1591 cloned.clone_from(&original);
1592
1593 assert_eq!(original, cloned);
1594 }
1595
1596 #[test]
1597 fn test_access_filters_clone() {
1598 let original = create_sample_access_filters();
1599 let cloned = original.clone();
1600
1601 assert_eq!(original, cloned);
1602 }
1603
1604 #[test]
1605 fn test_access_filters_clone_from() {
1606 let original = create_sample_access_filters();
1607 let mut cloned = AccessFilters::default();
1608
1609 cloned.with.insert(ComponentId::new(1));
1610 cloned.without.insert(ComponentId::new(2));
1611
1612 cloned.clone_from(&original);
1613
1614 assert_eq!(original, cloned);
1615 }
1616
1617 #[test]
1618 fn test_filtered_access_set_clone() {
1619 let original = create_sample_filtered_access_set();
1620 let cloned = original.clone();
1621
1622 assert_eq!(original, cloned);
1623 }
1624
1625 #[test]
1626 fn test_filtered_access_set_from() {
1627 let original = create_sample_filtered_access_set();
1628 let mut cloned = FilteredAccessSet::default();
1629
1630 cloned.add_unfiltered_component_read(ComponentId::new(7));
1631 cloned.add_unfiltered_component_write(ComponentId::new(9));
1632 cloned.write_all();
1633
1634 cloned.clone_from(&original);
1635
1636 assert_eq!(original, cloned);
1637 }
1638
1639 #[test]
1640 fn read_all_access_conflicts() {
1641 let mut access_a = Access::default();
1643 access_a.add_write(ComponentId::new(0));
1644
1645 let mut access_b = Access::default();
1646 access_b.read_all();
1647
1648 assert!(!access_b.is_compatible(&access_a));
1649
1650 let mut access_a = Access::default();
1652 access_a.read_all();
1653
1654 let mut access_b = Access::default();
1655 access_b.read_all();
1656
1657 assert!(access_b.is_compatible(&access_a));
1658 }
1659
1660 #[test]
1661 fn access_get_conflicts() {
1662 let mut access_a = Access::default();
1663 access_a.add_read(ComponentId::new(0));
1664 access_a.add_read(ComponentId::new(1));
1665
1666 let mut access_b = Access::default();
1667 access_b.add_read(ComponentId::new(0));
1668 access_b.add_write(ComponentId::new(1));
1669
1670 assert_eq!(
1671 access_a.get_conflicts(&access_b),
1672 vec![ComponentId::new(1)].into()
1673 );
1674
1675 let mut access_c = Access::default();
1676 access_c.add_write(ComponentId::new(0));
1677 access_c.add_write(ComponentId::new(1));
1678
1679 assert_eq!(
1680 access_a.get_conflicts(&access_c),
1681 vec![ComponentId::new(0), ComponentId::new(1)].into()
1682 );
1683 assert_eq!(
1684 access_b.get_conflicts(&access_c),
1685 vec![ComponentId::new(0), ComponentId::new(1)].into()
1686 );
1687
1688 let mut access_d = Access::default();
1689 access_d.add_read(ComponentId::new(0));
1690
1691 assert_eq!(access_d.get_conflicts(&access_a), AccessConflicts::empty());
1692 assert_eq!(access_d.get_conflicts(&access_b), AccessConflicts::empty());
1693 assert_eq!(
1694 access_d.get_conflicts(&access_c),
1695 vec![ComponentId::new(0)].into()
1696 );
1697 }
1698
1699 #[test]
1700 fn filtered_combined_access() {
1701 let mut access_a = FilteredAccessSet::default();
1702 access_a.add_unfiltered_component_read(ComponentId::new(1));
1703
1704 let mut filter_b = FilteredAccess::default();
1705 filter_b.add_write(ComponentId::new(1));
1706
1707 let conflicts = access_a.get_conflicts_single(&filter_b);
1708 assert_eq!(
1709 &conflicts,
1710 &AccessConflicts::from(vec![ComponentId::new(1)]),
1711 "access_a: {access_a:?}, filter_b: {filter_b:?}"
1712 );
1713 }
1714
1715 #[test]
1716 fn filtered_access_extend() {
1717 let mut access_a = FilteredAccess::default();
1718 access_a.add_read(ComponentId::new(0));
1719 access_a.add_read(ComponentId::new(1));
1720 access_a.and_with(ComponentId::new(2));
1721
1722 let mut access_b = FilteredAccess::default();
1723 access_b.add_read(ComponentId::new(0));
1724 access_b.add_write(ComponentId::new(3));
1725 access_b.and_without(ComponentId::new(4));
1726
1727 access_a.extend(&access_b);
1728
1729 let mut expected = FilteredAccess::default();
1730 expected.add_read(ComponentId::new(0));
1731 expected.add_read(ComponentId::new(1));
1732 expected.and_with(ComponentId::new(2));
1733 expected.add_write(ComponentId::new(3));
1734 expected.and_without(ComponentId::new(4));
1735
1736 assert!(access_a.eq(&expected));
1737 }
1738
1739 #[test]
1740 fn filtered_access_extend_or() {
1741 let mut access_a = FilteredAccess::default();
1742 access_a.add_write(ComponentId::new(0));
1744 access_a.add_write(ComponentId::new(1));
1745
1746 let mut access_b = FilteredAccess::default();
1748 access_b.and_with(ComponentId::new(2));
1749
1750 let mut access_c = FilteredAccess::default();
1752 access_c.and_with(ComponentId::new(3));
1753 access_c.and_without(ComponentId::new(4));
1754
1755 access_b.append_or(&access_c);
1757 access_a.extend(&access_b);
1760
1761 let mut expected = FilteredAccess::default();
1765 expected.add_write(ComponentId::new(0));
1766 expected.add_write(ComponentId::new(1));
1767 expected.filter_sets = vec![
1769 AccessFilters {
1770 with: ComponentIdSet::from_bits(FixedBitSet::with_capacity_and_blocks(3, [0b111])),
1771 without: ComponentIdSet::default(),
1772 },
1773 AccessFilters {
1774 with: ComponentIdSet::from_bits(FixedBitSet::with_capacity_and_blocks(4, [0b1011])),
1775 without: ComponentIdSet::from_bits(FixedBitSet::with_capacity_and_blocks(
1776 5,
1777 [0b10000],
1778 )),
1779 },
1780 ];
1781
1782 assert_eq!(access_a, expected);
1783 }
1784
1785 #[test]
1786 fn try_iter_component_access_simple() {
1787 let mut access = Access::default();
1788
1789 access.add_read(ComponentId::new(1));
1790 access.add_read(ComponentId::new(2));
1791 access.add_write(ComponentId::new(3));
1792 access.add_archetypal(ComponentId::new(5));
1793
1794 let result = access.try_iter_access().map(Iterator::collect::<Vec<_>>);
1795
1796 assert_eq!(
1797 result,
1798 Ok(vec![
1799 ComponentAccessKind::Shared(ComponentId::new(1)),
1800 ComponentAccessKind::Shared(ComponentId::new(2)),
1801 ComponentAccessKind::Exclusive(ComponentId::new(3)),
1802 ComponentAccessKind::Archetypal(ComponentId::new(5)),
1803 ]),
1804 );
1805 }
1806
1807 #[test]
1808 fn try_iter_component_access_unbounded_write_all() {
1809 let mut access = Access::default();
1810
1811 access.add_read(ComponentId::new(1));
1812 access.add_read(ComponentId::new(2));
1813 access.write_all();
1814
1815 let result = access.try_iter_access().map(Iterator::collect::<Vec<_>>);
1816
1817 assert_eq!(
1818 result,
1819 Err(UnboundedAccessError {
1820 writes_inverted: true,
1821 read_and_writes_inverted: true
1822 }),
1823 );
1824 }
1825
1826 #[test]
1827 fn try_iter_component_access_unbounded_read_all() {
1828 let mut access = Access::default();
1829
1830 access.add_read(ComponentId::new(1));
1831 access.add_read(ComponentId::new(2));
1832 access.read_all();
1833
1834 let result = access.try_iter_access().map(Iterator::collect::<Vec<_>>);
1835
1836 assert_eq!(
1837 result,
1838 Err(UnboundedAccessError {
1839 writes_inverted: false,
1840 read_and_writes_inverted: true
1841 }),
1842 );
1843 }
1844
1845 fn bit_set(bits: usize, iter: impl IntoIterator<Item = usize>) -> ComponentIdSet {
1848 let mut result = FixedBitSet::with_capacity(bits);
1849 result.extend(iter);
1850 ComponentIdSet::from_bits(result)
1851 }
1852
1853 #[test]
1854 fn invertible_union_with_tests() {
1855 let invertible_union = |mut self_inverted: bool, other_inverted: bool| {
1856 let mut self_set = bit_set(4, [0, 1]);
1858 let other_set = bit_set(4, [0, 2]);
1859 invertible_union_with(
1860 &mut self_set,
1861 &mut self_inverted,
1862 &other_set,
1863 other_inverted,
1864 );
1865 (self_set, self_inverted)
1866 };
1867
1868 let (s, i) = invertible_union(false, false);
1870 assert_eq!((s, i), (bit_set(4, [0, 1, 2]), false));
1872
1873 let (s, i) = invertible_union(false, true);
1874 assert_eq!((s, i), (bit_set(4, [2]), true));
1876
1877 let (s, i) = invertible_union(true, false);
1878 assert_eq!((s, i), (bit_set(4, [1]), true));
1880
1881 let (s, i) = invertible_union(true, true);
1882 assert_eq!((s, i), (bit_set(4, [0]), true));
1884 }
1885
1886 #[test]
1887 fn invertible_union_with_different_lengths() {
1888 let mut self_set = bit_set(1, [0]);
1893 let mut self_inverted = false;
1894 let other_set = bit_set(3, [0, 1]);
1895 let other_inverted = true;
1896 invertible_union_with(
1897 &mut self_set,
1898 &mut self_inverted,
1899 &other_set,
1900 other_inverted,
1901 );
1902
1903 assert_eq!((self_set, self_inverted), (bit_set(3, [1]), true));
1905 }
1906
1907 #[test]
1908 fn invertible_difference_with_tests() {
1909 let invertible_difference = |mut self_inverted: bool, other_inverted: bool| {
1910 let mut self_set = bit_set(4, [0, 1]);
1912 let other_set = bit_set(4, [0, 2]);
1913 invertible_difference_with(
1914 &mut self_set,
1915 &mut self_inverted,
1916 &other_set,
1917 other_inverted,
1918 );
1919 (self_set, self_inverted)
1920 };
1921
1922 let (s, i) = invertible_difference(false, false);
1924 assert_eq!((s, i), (bit_set(4, [1]), false));
1926
1927 let (s, i) = invertible_difference(false, true);
1928 assert_eq!((s, i), (bit_set(4, [0]), false));
1930
1931 let (s, i) = invertible_difference(true, false);
1932 assert_eq!((s, i), (bit_set(4, [0, 1, 2]), true));
1934
1935 let (s, i) = invertible_difference(true, true);
1936 assert_eq!((s, i), (bit_set(4, [2]), false));
1938 }
1939
1940 #[test]
1941 fn component_id_set_insert_remove_clear() {
1942 let mut set = ComponentIdSet::new();
1943 assert!(!set.contains(ComponentId::new(0)));
1944 assert!(!set.contains(ComponentId::new(1)));
1945 assert!(!set.contains(ComponentId::new(2)));
1946 assert!(set.is_clear());
1947 set.insert(ComponentId::new(2));
1948 set.insert(ComponentId::new(1));
1949 assert!(!set.contains(ComponentId::new(0)));
1950 assert!(set.contains(ComponentId::new(1)));
1951 assert!(set.contains(ComponentId::new(2)));
1952 assert!(!set.is_clear());
1953 set.remove(ComponentId::new(1));
1954 assert!(!set.contains(ComponentId::new(0)));
1955 assert!(!set.contains(ComponentId::new(1)));
1956 assert!(set.contains(ComponentId::new(2)));
1957 assert!(!set.is_clear());
1958 set.insert(ComponentId::new(2));
1959 set.insert(ComponentId::new(1));
1960 assert!(!set.contains(ComponentId::new(0)));
1961 assert!(set.contains(ComponentId::new(1)));
1962 assert!(set.contains(ComponentId::new(2)));
1963 assert!(!set.is_clear());
1964 set.clear();
1965 assert!(!set.contains(ComponentId::new(0)));
1966 assert!(!set.contains(ComponentId::new(1)));
1967 assert!(!set.contains(ComponentId::new(2)));
1968 assert!(set.is_clear());
1969 }
1970
1971 #[test]
1972 fn component_id_set_remove_out_of_range() {
1973 let mut set = ComponentIdSet::new();
1974 set.remove(ComponentId::new(3));
1975 set.insert(ComponentId::new(1));
1976 set.remove(ComponentId::new(4));
1977 assert!(set.iter().eq([1].map(ComponentId::new)));
1978 }
1979
1980 #[test]
1981 fn component_id_set_is_subset_is_disjoint() {
1982 let set_1234 = ComponentIdSet::from_iter([1, 2, 3, 4].map(ComponentId::new));
1983 let set_23 = ComponentIdSet::from_iter([2, 3].map(ComponentId::new));
1984 let set_45 = ComponentIdSet::from_iter([4, 5].map(ComponentId::new));
1985 assert!(set_23.is_subset(&set_1234));
1986 assert!(!set_1234.is_subset(&set_23));
1987 assert!(set_23.is_disjoint(&set_45));
1988 assert!(set_45.is_disjoint(&set_23));
1989 assert!(!set_1234.is_disjoint(&set_23));
1990 assert!(!set_23.is_disjoint(&set_1234));
1991 }
1992
1993 #[test]
1994 fn component_id_set_union_intersection_difference() {
1995 let set_13 = ComponentIdSet::from_iter([1, 3].map(ComponentId::new));
1996 let set_23 = ComponentIdSet::from_iter([2, 3].map(ComponentId::new));
1997
1998 assert!(set_13.union(&set_23).eq([1, 3, 2].map(ComponentId::new)));
1999 assert!(set_23.union(&set_13).eq([2, 3, 1].map(ComponentId::new)));
2000 assert!(set_13.intersection(&set_23).eq([3].map(ComponentId::new)));
2001 assert!(set_23.intersection(&set_13).eq([3].map(ComponentId::new)));
2002 assert!(set_13.difference(&set_23).eq([1].map(ComponentId::new)));
2003 assert!(set_23.difference(&set_13).eq([2].map(ComponentId::new)));
2004 }
2005
2006 #[test]
2007 fn component_id_set_union_intersection_difference_with() {
2008 let set_13 = ComponentIdSet::from_iter([1, 3].map(ComponentId::new));
2009 let set_23 = ComponentIdSet::from_iter([2, 3].map(ComponentId::new));
2010
2011 let mut s = set_13.clone();
2012 s.union_with(&set_23);
2013 assert!(s.iter().eq([1, 2, 3].map(ComponentId::new)));
2014
2015 let mut s = set_23.clone();
2016 s.union_with(&set_13);
2017 assert!(s.iter().eq([1, 2, 3].map(ComponentId::new)));
2018
2019 let mut s = set_13.clone();
2020 s.intersect_with(&set_23);
2021 assert!(s.iter().eq([3].map(ComponentId::new)));
2022
2023 let mut s = set_23.clone();
2024 s.intersect_with(&set_13);
2025 assert!(s.iter().eq([3].map(ComponentId::new)));
2026
2027 let mut s = set_13.clone();
2028 s.difference_with(&set_23);
2029 assert!(s.iter().eq([1].map(ComponentId::new)));
2030
2031 let mut s = set_23.clone();
2032 s.difference_with(&set_13);
2033 assert!(s.iter().eq([2].map(ComponentId::new)));
2034
2035 let mut s = set_13.clone();
2036 s.difference_from(&set_23);
2037 assert!(s.iter().eq([2].map(ComponentId::new)));
2038
2039 let mut s = set_23.clone();
2040 s.difference_from(&set_13);
2041 assert!(s.iter().eq([1].map(ComponentId::new)));
2042 }
2043}