linked_hash_set/lib.rs
1//! A linked hash set implementation based on the `linked_hash_map` crate.
2//! See [`LinkedHashSet`](struct.LinkedHashSet.html).
3//!
4//! # Examples
5//!
6//! ```
7//! let mut set = linked_hash_set::LinkedHashSet::new();
8//! assert!(set.insert(234));
9//! assert!(set.insert(123));
10//! assert!(set.insert(345));
11//! assert!(!set.insert(123)); // Also see `insert_if_absent` which won't change order
12//!
13//! assert_eq!(set.into_iter().collect::<Vec<_>>(), vec![234, 345, 123]);
14//! ```
15#[cfg(feature = "serde")]
16pub mod serde;
17
18use linked_hash_map as map;
19use linked_hash_map::{Keys, LinkedHashMap};
20use std::borrow::Borrow;
21use std::collections::hash_map::RandomState;
22use std::fmt;
23use std::hash::{BuildHasher, Hash, Hasher};
24use std::iter::{Chain, FromIterator};
25use std::ops::{BitAnd, BitOr, BitXor, Sub};
26
27// Note: This implementation is adapted from std `HashSet` implementation ~2017-10
28// parts relying on std `HashMap` functionality that is not present in `LinkedHashMap` or
29// relying on private access to map internals have been removed.
30
31/// A linked hash set implemented as a `linked_hash_map::LinkedHashMap` where the value is
32/// `()`, in a similar way std `HashSet` is implemented from `HashMap`.
33///
34/// General usage is very similar to a std `HashSet`. However, a `LinkedHashSet` **maintains
35/// insertion order** using a doubly-linked list running through its entries. As such methods
36/// [`front()`], [`pop_front()`], [`back()`] and [`pop_back()`] are provided.
37///
38/// # Examples
39///
40/// ```
41/// use linked_hash_set::LinkedHashSet;
42/// // Type inference lets us omit an explicit type signature (which
43/// // would be `LinkedHashSet<&str>` in this example).
44/// let mut books = LinkedHashSet::new();
45///
46/// // Add some books.
47/// books.insert("A Dance With Dragons");
48/// books.insert("To Kill a Mockingbird");
49/// books.insert("The Odyssey");
50/// books.insert("The Great Gatsby");
51///
52/// // Check for a specific one.
53/// if !books.contains("The Winds of Winter") {
54/// println!(
55/// "We have {} books, but The Winds of Winter ain't one.",
56/// books.len()
57/// );
58/// }
59///
60/// // Remove a book.
61/// books.remove("The Odyssey");
62///
63/// // Remove the first inserted book.
64/// books.pop_front();
65///
66/// // Iterate over the remaining books in insertion order.
67/// for book in &books {
68/// println!("{}", book);
69/// }
70///
71/// assert_eq!(
72/// books.into_iter().collect::<Vec<_>>(),
73/// vec!["To Kill a Mockingbird", "The Great Gatsby"]
74/// );
75/// ```
76///
77/// The easiest way to use `LinkedHashSet` with a custom type is to derive
78/// `Eq` and `Hash`. We must also derive `PartialEq`, this will in the
79/// future be implied by `Eq`.
80///
81/// ```
82/// use linked_hash_set::LinkedHashSet;
83/// #[derive(Hash, Eq, PartialEq, Debug)]
84/// struct Viking<'a> {
85/// name: &'a str,
86/// power: usize,
87/// }
88///
89/// let mut vikings = LinkedHashSet::new();
90///
91/// vikings.insert(Viking {
92/// name: "Einar",
93/// power: 9,
94/// });
95/// vikings.insert(Viking {
96/// name: "Einar",
97/// power: 9,
98/// });
99/// vikings.insert(Viking {
100/// name: "Olaf",
101/// power: 4,
102/// });
103/// vikings.insert(Viking {
104/// name: "Harald",
105/// power: 8,
106/// });
107///
108/// // Use derived implementation to print the vikings.
109/// for x in &vikings {
110/// println!("{:?}", x);
111/// }
112/// ```
113///
114/// A `LinkedHashSet` with fixed list of elements can be initialized from an array:
115///
116/// ```
117/// use linked_hash_set::LinkedHashSet;
118///
119/// fn main() {
120/// let viking_names: LinkedHashSet<&str> =
121/// ["Einar", "Olaf", "Harald"].iter().cloned().collect();
122/// // use the values stored in the set
123/// }
124/// ```
125///
126/// [`front()`]: struct.LinkedHashSet.html#method.front
127/// [`pop_front()`]: struct.LinkedHashSet.html#method.pop_front
128/// [`back()`]: struct.LinkedHashSet.html#method.back
129/// [`pop_back()`]: struct.LinkedHashSet.html#method.pop_back
130pub struct LinkedHashSet<T, S = RandomState> {
131 map: LinkedHashMap<T, (), S>,
132}
133
134impl<T: Hash + Eq> LinkedHashSet<T, RandomState> {
135 /// Creates an empty `LinkedHashSet`.
136 ///
137 /// # Examples
138 ///
139 /// ```
140 /// use linked_hash_set::LinkedHashSet;
141 /// let set: LinkedHashSet<i32> = LinkedHashSet::new();
142 /// ```
143 #[inline]
144 pub fn new() -> LinkedHashSet<T, RandomState> {
145 LinkedHashSet {
146 map: LinkedHashMap::new(),
147 }
148 }
149
150 /// Creates an empty `LinkedHashSet` with the specified capacity.
151 ///
152 /// The hash set will be able to hold at least `capacity` elements without
153 /// reallocating. If `capacity` is 0, the hash set will not allocate.
154 ///
155 /// # Examples
156 ///
157 /// ```
158 /// use linked_hash_set::LinkedHashSet;
159 /// let set: LinkedHashSet<i32> = LinkedHashSet::with_capacity(10);
160 /// assert!(set.capacity() >= 10);
161 /// ```
162 #[inline]
163 pub fn with_capacity(capacity: usize) -> LinkedHashSet<T, RandomState> {
164 LinkedHashSet {
165 map: LinkedHashMap::with_capacity(capacity),
166 }
167 }
168}
169
170impl<T, S> LinkedHashSet<T, S>
171where
172 T: Eq + Hash,
173 S: BuildHasher,
174{
175 /// Creates a new empty hash set which will use the given hasher to hash
176 /// keys.
177 ///
178 /// The hash set is also created with the default initial capacity.
179 ///
180 /// Warning: `hasher` is normally randomly generated, and
181 /// is designed to allow `LinkedHashSet`s to be resistant to attacks that
182 /// cause many collisions and very poor performance. Setting it
183 /// manually using this function can expose a DoS attack vector.
184 ///
185 /// # Examples
186 ///
187 /// ```
188 /// use linked_hash_set::LinkedHashSet;
189 /// use std::collections::hash_map::RandomState;
190 ///
191 /// let s = RandomState::new();
192 /// let mut set = LinkedHashSet::with_hasher(s);
193 /// set.insert(2);
194 /// ```
195 #[inline]
196 pub fn with_hasher(hasher: S) -> LinkedHashSet<T, S> {
197 LinkedHashSet {
198 map: LinkedHashMap::with_hasher(hasher),
199 }
200 }
201
202 /// Creates an empty `LinkedHashSet` with with the specified capacity, using
203 /// `hasher` to hash the keys.
204 ///
205 /// The hash set will be able to hold at least `capacity` elements without
206 /// reallocating. If `capacity` is 0, the hash set will not allocate.
207 ///
208 /// Warning: `hasher` is normally randomly generated, and
209 /// is designed to allow `LinkedHashSet`s to be resistant to attacks that
210 /// cause many collisions and very poor performance. Setting it
211 /// manually using this function can expose a DoS attack vector.
212 ///
213 /// # Examples
214 ///
215 /// ```
216 /// use linked_hash_set::LinkedHashSet;
217 /// use std::collections::hash_map::RandomState;
218 ///
219 /// let s = RandomState::new();
220 /// let mut set = LinkedHashSet::with_capacity_and_hasher(10, s);
221 /// set.insert(1);
222 /// ```
223 #[inline]
224 pub fn with_capacity_and_hasher(capacity: usize, hasher: S) -> LinkedHashSet<T, S> {
225 LinkedHashSet {
226 map: LinkedHashMap::with_capacity_and_hasher(capacity, hasher),
227 }
228 }
229
230 /// Returns a reference to the set's `BuildHasher`.
231 ///
232 /// # Examples
233 ///
234 /// ```
235 /// use linked_hash_set::LinkedHashSet;
236 /// use std::collections::hash_map::RandomState;
237 ///
238 /// let hasher = RandomState::new();
239 /// let set: LinkedHashSet<i32> = LinkedHashSet::with_hasher(hasher);
240 /// let hasher: &RandomState = set.hasher();
241 /// ```
242 pub fn hasher(&self) -> &S {
243 self.map.hasher()
244 }
245
246 /// Returns the number of elements the set can hold without reallocating.
247 ///
248 /// # Examples
249 ///
250 /// ```
251 /// use linked_hash_set::LinkedHashSet;
252 /// let set: LinkedHashSet<i32> = LinkedHashSet::with_capacity(100);
253 /// assert!(set.capacity() >= 100);
254 /// ```
255 #[inline]
256 pub fn capacity(&self) -> usize {
257 self.map.capacity()
258 }
259
260 /// Reserves capacity for at least `additional` more elements to be inserted
261 /// in the `LinkedHashSet`. The collection may reserve more space to avoid
262 /// frequent reallocations.
263 ///
264 /// # Panics
265 ///
266 /// Panics if the new allocation size overflows `usize`.
267 ///
268 /// # Examples
269 ///
270 /// ```
271 /// use linked_hash_set::LinkedHashSet;
272 /// let mut set: LinkedHashSet<i32> = LinkedHashSet::new();
273 /// set.reserve(10);
274 /// assert!(set.capacity() >= 10);
275 /// ```
276 pub fn reserve(&mut self, additional: usize) {
277 self.map.reserve(additional)
278 }
279
280 /// Shrinks the capacity of the set as much as possible. It will drop
281 /// down as much as possible while maintaining the internal rules
282 /// and possibly leaving some space in accordance with the resize policy.
283 ///
284 /// # Examples
285 ///
286 /// ```
287 /// use linked_hash_set::LinkedHashSet;
288 ///
289 /// let mut set = LinkedHashSet::with_capacity(100);
290 /// set.insert(1);
291 /// set.insert(2);
292 /// assert!(set.capacity() >= 100);
293 /// set.shrink_to_fit();
294 /// assert!(set.capacity() >= 2);
295 /// ```
296 pub fn shrink_to_fit(&mut self) {
297 self.map.shrink_to_fit()
298 }
299
300 /// An iterator visiting all elements in insertion order.
301 /// The iterator element type is `&'a T`.
302 ///
303 /// # Examples
304 ///
305 /// ```
306 /// use linked_hash_set::LinkedHashSet;
307 /// let mut set = LinkedHashSet::new();
308 /// set.insert("a");
309 /// set.insert("b");
310 ///
311 /// // Will print in an insertion order.
312 /// for x in set.iter() {
313 /// println!("{}", x);
314 /// }
315 /// ```
316 pub fn iter(&self) -> Iter<'_, T> {
317 Iter {
318 iter: self.map.keys(),
319 }
320 }
321
322 /// Visits the values representing the difference,
323 /// i.e. the values that are in `self` but not in `other`.
324 ///
325 /// # Examples
326 ///
327 /// ```
328 /// use linked_hash_set::LinkedHashSet;
329 /// let a: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
330 /// let b: LinkedHashSet<_> = [4, 2, 3, 4].iter().cloned().collect();
331 ///
332 /// // Can be seen as `a - b`.
333 /// for x in a.difference(&b) {
334 /// println!("{}", x); // Print 1
335 /// }
336 ///
337 /// let diff: LinkedHashSet<_> = a.difference(&b).collect();
338 /// assert_eq!(diff, [1].iter().collect());
339 ///
340 /// // Note that difference is not symmetric,
341 /// // and `b - a` means something else:
342 /// let diff: LinkedHashSet<_> = b.difference(&a).collect();
343 /// assert_eq!(diff, [4].iter().collect());
344 /// ```
345 pub fn difference<'a>(&'a self, other: &'a LinkedHashSet<T, S>) -> Difference<'a, T, S> {
346 Difference {
347 iter: self.iter(),
348 other,
349 }
350 }
351
352 /// Visits the values representing the symmetric difference,
353 /// i.e. the values that are in `self` or in `other` but not in both.
354 ///
355 /// # Examples
356 ///
357 /// ```
358 /// use linked_hash_set::LinkedHashSet;
359 /// let a: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
360 /// let b: LinkedHashSet<_> = [4, 2, 3, 4].iter().cloned().collect();
361 ///
362 /// // Print 1, 4 in insertion order.
363 /// for x in a.symmetric_difference(&b) {
364 /// println!("{}", x);
365 /// }
366 ///
367 /// let diff1: LinkedHashSet<_> = a.symmetric_difference(&b).collect();
368 /// let diff2: LinkedHashSet<_> = b.symmetric_difference(&a).collect();
369 ///
370 /// assert_eq!(diff1, diff2);
371 /// assert_eq!(diff1, [1, 4].iter().collect());
372 /// ```
373 pub fn symmetric_difference<'a>(
374 &'a self,
375 other: &'a LinkedHashSet<T, S>,
376 ) -> SymmetricDifference<'a, T, S> {
377 SymmetricDifference {
378 iter: self.difference(other).chain(other.difference(self)),
379 }
380 }
381
382 /// Visits the values representing the intersection,
383 /// i.e. the values that are both in `self` and `other`.
384 ///
385 /// # Examples
386 ///
387 /// ```
388 /// use linked_hash_set::LinkedHashSet;
389 /// let a: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
390 /// let b: LinkedHashSet<_> = [4, 2, 3, 4].iter().cloned().collect();
391 ///
392 /// // Print 2, 3 in insertion order.
393 /// for x in a.intersection(&b) {
394 /// println!("{}", x);
395 /// }
396 ///
397 /// let intersection: LinkedHashSet<_> = a.intersection(&b).collect();
398 /// assert_eq!(intersection, [2, 3].iter().collect());
399 /// ```
400 pub fn intersection<'a>(&'a self, other: &'a LinkedHashSet<T, S>) -> Intersection<'a, T, S> {
401 Intersection {
402 iter: self.iter(),
403 other,
404 }
405 }
406
407 /// Visits the values representing the union,
408 /// i.e. all the values in `self` or `other`, without duplicates.
409 ///
410 /// # Examples
411 ///
412 /// ```
413 /// use linked_hash_set::LinkedHashSet;
414 /// let a: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
415 /// let b: LinkedHashSet<_> = [4, 2, 3, 4].iter().cloned().collect();
416 ///
417 /// // Print 1, 2, 3, 4 in insertion order.
418 /// for x in a.union(&b) {
419 /// println!("{}", x);
420 /// }
421 ///
422 /// let union: LinkedHashSet<_> = a.union(&b).collect();
423 /// assert_eq!(union, [1, 2, 3, 4].iter().collect());
424 /// ```
425 pub fn union<'a>(&'a self, other: &'a LinkedHashSet<T, S>) -> Union<'a, T, S> {
426 Union {
427 iter: self.iter().chain(other.difference(self)),
428 }
429 }
430
431 /// Returns the number of elements in the set.
432 ///
433 /// # Examples
434 ///
435 /// ```
436 /// use linked_hash_set::LinkedHashSet;
437 ///
438 /// let mut v = LinkedHashSet::new();
439 /// assert_eq!(v.len(), 0);
440 /// v.insert(1);
441 /// assert_eq!(v.len(), 1);
442 /// ```
443 pub fn len(&self) -> usize {
444 self.map.len()
445 }
446
447 /// Returns true if the set contains no elements.
448 ///
449 /// # Examples
450 ///
451 /// ```
452 /// use linked_hash_set::LinkedHashSet;
453 ///
454 /// let mut v = LinkedHashSet::new();
455 /// assert!(v.is_empty());
456 /// v.insert(1);
457 /// assert!(!v.is_empty());
458 /// ```
459 pub fn is_empty(&self) -> bool {
460 self.map.is_empty()
461 }
462
463 // TODO not in linked_hash_map
464 // /// Clears the set, returning all elements in an iterator.
465 // ///
466 // /// # Examples
467 // ///
468 // /// ```
469 // /// use linked_hash_set::LinkedHashSet;
470 // ///
471 // /// let mut set: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
472 // /// assert!(!set.is_empty());
473 // ///
474 // /// // print 1, 2, 3 in an insertion order
475 // /// for i in set.drain() {
476 // /// println!("{}", i);
477 // /// }
478 // ///
479 // /// assert!(set.is_empty());
480 // /// ```
481 // #[inline]
482 // pub fn drain(&mut self) -> Drain<T> {
483 // Drain { iter: self.map.drain() }
484 // }
485
486 /// Clears the set, removing all values.
487 ///
488 /// # Examples
489 ///
490 /// ```
491 /// use linked_hash_set::LinkedHashSet;
492 ///
493 /// let mut v = LinkedHashSet::new();
494 /// v.insert(1);
495 /// v.clear();
496 /// assert!(v.is_empty());
497 /// ```
498 pub fn clear(&mut self) {
499 self.map.clear()
500 }
501
502 /// Returns `true` if the set contains a value.
503 ///
504 /// The value may be any borrowed form of the set's value type, but
505 /// `Hash` and `Eq` on the borrowed form *must* match those for
506 /// the value type.
507 ///
508 /// # Examples
509 ///
510 /// ```
511 /// use linked_hash_set::LinkedHashSet;
512 ///
513 /// let set: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
514 /// assert_eq!(set.contains(&1), true);
515 /// assert_eq!(set.contains(&4), false);
516 /// ```
517 pub fn contains<Q: ?Sized>(&self, value: &Q) -> bool
518 where
519 T: Borrow<Q>,
520 Q: Hash + Eq,
521 {
522 self.map.contains_key(value)
523 }
524
525 /// If already present, moves a value to the end of the ordering.
526 ///
527 /// If the set did have this value present, `true` is returned.
528 ///
529 /// If the set did not have this value present, `false` is returned.
530 ///
531 /// Similar to `LinkedHashMap::get_refresh`.
532 ///
533 /// # Examples
534 ///
535 /// ```
536 /// use linked_hash_set::LinkedHashSet;
537 ///
538 /// let mut set: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
539 /// let was_refreshed = set.refresh(&2);
540 ///
541 /// assert_eq!(was_refreshed, true);
542 /// assert_eq!(set.into_iter().collect::<Vec<_>>(), vec![1, 3, 2]);
543 /// ```
544 pub fn refresh<Q: ?Sized>(&mut self, value: &Q) -> bool
545 where
546 T: Borrow<Q>,
547 Q: Hash + Eq,
548 {
549 self.map.get_refresh(value).is_some()
550 }
551
552 // TODO Non-trivial port without private access to map
553 // /// Returns a reference to the value in the set, if any, that is equal to the given value.
554 // ///
555 // /// The value may be any borrowed form of the set's value type, but
556 // /// `Hash` and `Eq` on the borrowed form *must* match those for
557 // /// the value type.
558 // pub fn get<Q: ?Sized>(&self, value: &Q) -> Option<&T>
559 // where T: Borrow<Q>,
560 // Q: Hash + Eq
561 // {
562 // Recover::get(&self.map, value)
563 // }
564
565 /// Returns `true` if `self` has no elements in common with `other`.
566 /// This is equivalent to checking for an empty intersection.
567 ///
568 /// # Examples
569 ///
570 /// ```
571 /// use linked_hash_set::LinkedHashSet;
572 ///
573 /// let a: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
574 /// let mut b = LinkedHashSet::new();
575 ///
576 /// assert_eq!(a.is_disjoint(&b), true);
577 /// b.insert(4);
578 /// assert_eq!(a.is_disjoint(&b), true);
579 /// b.insert(1);
580 /// assert_eq!(a.is_disjoint(&b), false);
581 /// ```
582 pub fn is_disjoint(&self, other: &LinkedHashSet<T, S>) -> bool {
583 self.iter().all(|v| !other.contains(v))
584 }
585
586 /// Returns `true` if the set is a subset of another,
587 /// i.e. `other` contains at least all the values in `self`.
588 ///
589 /// # Examples
590 ///
591 /// ```
592 /// use linked_hash_set::LinkedHashSet;
593 ///
594 /// let sup: LinkedHashSet<_> = [1, 2, 3].iter().cloned().collect();
595 /// let mut set = LinkedHashSet::new();
596 ///
597 /// assert_eq!(set.is_subset(&sup), true);
598 /// set.insert(2);
599 /// assert_eq!(set.is_subset(&sup), true);
600 /// set.insert(4);
601 /// assert_eq!(set.is_subset(&sup), false);
602 /// ```
603 pub fn is_subset(&self, other: &LinkedHashSet<T, S>) -> bool {
604 self.iter().all(|v| other.contains(v))
605 }
606
607 /// Returns `true` if the set is a superset of another,
608 /// i.e. `self` contains at least all the values in `other`.
609 ///
610 /// # Examples
611 ///
612 /// ```
613 /// use linked_hash_set::LinkedHashSet;
614 ///
615 /// let sub: LinkedHashSet<_> = [1, 2].iter().cloned().collect();
616 /// let mut set = LinkedHashSet::new();
617 ///
618 /// assert_eq!(set.is_superset(&sub), false);
619 ///
620 /// set.insert(0);
621 /// set.insert(1);
622 /// assert_eq!(set.is_superset(&sub), false);
623 ///
624 /// set.insert(2);
625 /// assert_eq!(set.is_superset(&sub), true);
626 /// ```
627 #[inline]
628 pub fn is_superset(&self, other: &LinkedHashSet<T, S>) -> bool {
629 other.is_subset(self)
630 }
631
632 /// Adds a value to the set.
633 ///
634 /// If the set did not have this value present, `true` is returned.
635 ///
636 /// If the set did have this value present, `false` is returned.
637 ///
638 /// Note that performing this action will always place the value at the end of the ordering
639 /// whether the set already contained the value or not. Also see
640 /// [`insert_if_absent`](#method.insert_if_absent).
641 ///
642 /// # Examples
643 ///
644 /// ```
645 /// use linked_hash_set::LinkedHashSet;
646 ///
647 /// let mut set = LinkedHashSet::new();
648 ///
649 /// assert_eq!(set.insert(2), true);
650 /// assert_eq!(set.insert(2), false);
651 /// assert_eq!(set.len(), 1);
652 /// ```
653 pub fn insert(&mut self, value: T) -> bool {
654 self.map.insert(value, ()).is_none()
655 }
656
657 /// Adds a value to the set, if not already present. The distinction with `insert` is that
658 /// order of elements is unaffected when calling this method for a value already contained.
659 ///
660 /// If the set did not have this value present, `true` is returned.
661 ///
662 /// If the set did have this value present, `false` is returned.
663 ///
664 /// # Examples
665 ///
666 /// ```
667 /// use linked_hash_set::LinkedHashSet;
668 ///
669 /// let mut set = LinkedHashSet::new();
670 ///
671 /// assert_eq!(set.insert_if_absent(2), true);
672 /// assert_eq!(set.insert_if_absent(2), false);
673 /// assert_eq!(set.len(), 1);
674 /// ```
675 pub fn insert_if_absent(&mut self, value: T) -> bool {
676 if !self.map.contains_key(&value) {
677 self.map.insert(value, ()).is_none()
678 } else {
679 false
680 }
681 }
682
683 // TODO Non-trivial port without private access to map
684 // /// Adds a value to the set, replacing the existing value, if any, that is equal to the given
685 // /// one. Returns the replaced value.
686 // pub fn replace(&mut self, value: T) -> Option<T> {
687 // Recover::replace(&mut self.map, value)
688 // }
689
690 /// Removes a value from the set. Returns `true` if the value was
691 /// present in the set.
692 ///
693 /// The value may be any borrowed form of the set's value type, but
694 /// `Hash` and `Eq` on the borrowed form *must* match those for
695 /// the value type.
696 ///
697 /// This operation will not affect the ordering of the other elements.
698 ///
699 /// # Examples
700 ///
701 /// ```
702 /// use linked_hash_set::LinkedHashSet;
703 ///
704 /// let mut set = LinkedHashSet::new();
705 ///
706 /// set.insert(2);
707 /// assert_eq!(set.remove(&2), true);
708 /// assert_eq!(set.remove(&2), false);
709 /// ```
710 pub fn remove<Q: ?Sized>(&mut self, value: &Q) -> bool
711 where
712 T: Borrow<Q>,
713 Q: Hash + Eq,
714 {
715 self.map.remove(value).is_some()
716 }
717
718 // TODO Non-trivial port without private access to map
719 // /// Removes and returns the value in the set, if any, that is equal to the given one.
720 // ///
721 // /// The value may be any borrowed form of the set's value type, but
722 // /// `Hash` and `Eq` on the borrowed form *must* match those for
723 // /// the value type.
724 // pub fn take<Q: ?Sized>(&mut self, value: &Q) -> Option<T>
725 // where T: Borrow<Q>,
726 // Q: Hash + Eq
727 // {
728 // Recover::take(&mut self.map, value)
729 // }
730
731 // TODO not in linked_hash_map
732 // /// Retains only the elements specified by the predicate.
733 // ///
734 // /// In other words, remove all elements `e` such that `f(&e)` returns `false`.
735 // ///
736 // /// # Examples
737 // ///
738 // /// ```
739 // /// use linked_hash_set::LinkedHashSet;
740 // ///
741 // /// let xs = [1,2,3,4,5,6];
742 // /// let mut set: LinkedHashSet<isize> = xs.iter().cloned().collect();
743 // /// set.retain(|&k| k % 2 == 0);
744 // /// assert_eq!(set.len(), 3);
745 // /// ```
746 // pub fn retain<F>(&mut self, mut f: F)
747 // where F: FnMut(&T) -> bool
748 // {
749 // self.map.retain(|k, _| f(k));
750 // }
751
752 /// Gets the first entry.
753 pub fn front(&self) -> Option<&T> {
754 self.map.front().map(|(k, _)| k)
755 }
756
757 /// Removes the first entry.
758 pub fn pop_front(&mut self) -> Option<T> {
759 self.map.pop_front().map(|(k, _)| k)
760 }
761
762 /// Gets the last entry.
763 pub fn back(&mut self) -> Option<&T> {
764 self.map.back().map(|(k, _)| k)
765 }
766
767 /// Removes the last entry.
768 pub fn pop_back(&mut self) -> Option<T> {
769 self.map.pop_back().map(|(k, _)| k)
770 }
771}
772
773impl<T: Hash + Eq + Clone, S: BuildHasher + Clone> Clone for LinkedHashSet<T, S> {
774 fn clone(&self) -> Self {
775 let map = self.map.clone();
776 Self { map }
777 }
778}
779
780impl<T, S> PartialEq for LinkedHashSet<T, S>
781where
782 T: Eq + Hash,
783 S: BuildHasher,
784{
785 fn eq(&self, other: &LinkedHashSet<T, S>) -> bool {
786 if self.len() != other.len() {
787 return false;
788 }
789
790 self.iter().all(|key| other.contains(key))
791 }
792}
793
794impl<T, S> Hash for LinkedHashSet<T, S>
795where
796 T: Eq + Hash,
797 S: BuildHasher,
798{
799 fn hash<H: Hasher>(&self, state: &mut H) {
800 for e in self {
801 e.hash(state);
802 }
803 }
804}
805
806impl<T, S> Eq for LinkedHashSet<T, S>
807where
808 T: Eq + Hash,
809 S: BuildHasher,
810{
811}
812
813impl<T, S> fmt::Debug for LinkedHashSet<T, S>
814where
815 T: Eq + Hash + fmt::Debug,
816 S: BuildHasher,
817{
818 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
819 f.debug_set().entries(self.iter()).finish()
820 }
821}
822
823impl<T, S> FromIterator<T> for LinkedHashSet<T, S>
824where
825 T: Eq + Hash,
826 S: BuildHasher + Default,
827{
828 fn from_iter<I: IntoIterator<Item = T>>(iter: I) -> LinkedHashSet<T, S> {
829 let mut set = LinkedHashSet::with_hasher(Default::default());
830 set.extend(iter);
831 set
832 }
833}
834
835impl<T, S> Extend<T> for LinkedHashSet<T, S>
836where
837 T: Eq + Hash,
838 S: BuildHasher,
839{
840 fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {
841 self.map.extend(iter.into_iter().map(|k| (k, ())));
842 }
843}
844
845impl<'a, T, S> Extend<&'a T> for LinkedHashSet<T, S>
846where
847 T: 'a + Eq + Hash + Copy,
848 S: BuildHasher,
849{
850 fn extend<I: IntoIterator<Item = &'a T>>(&mut self, iter: I) {
851 self.extend(iter.into_iter().cloned());
852 }
853}
854
855impl<T, S> Default for LinkedHashSet<T, S>
856where
857 T: Eq + Hash,
858 S: BuildHasher + Default,
859{
860 /// Creates an empty `LinkedHashSet<T, S>` with the `Default` value for the hasher.
861 fn default() -> LinkedHashSet<T, S> {
862 LinkedHashSet {
863 map: LinkedHashMap::default(),
864 }
865 }
866}
867
868impl<'a, 'b, T, S> BitOr<&'b LinkedHashSet<T, S>> for &'a LinkedHashSet<T, S>
869where
870 T: Eq + Hash + Clone,
871 S: BuildHasher + Default,
872{
873 type Output = LinkedHashSet<T, S>;
874
875 /// Returns the union of `self` and `rhs` as a new `LinkedHashSet<T, S>`.
876 ///
877 /// # Examples
878 ///
879 /// ```
880 /// use linked_hash_set::LinkedHashSet;
881 ///
882 /// let a: LinkedHashSet<_> = vec![1, 2, 3].into_iter().collect();
883 /// let b: LinkedHashSet<_> = vec![3, 4, 5].into_iter().collect();
884 ///
885 /// let set = &a | &b;
886 ///
887 /// let mut i = 0;
888 /// let expected = [1, 2, 3, 4, 5];
889 /// for x in &set {
890 /// assert!(expected.contains(x));
891 /// i += 1;
892 /// }
893 /// assert_eq!(i, expected.len());
894 /// ```
895 fn bitor(self, rhs: &LinkedHashSet<T, S>) -> LinkedHashSet<T, S> {
896 self.union(rhs).cloned().collect()
897 }
898}
899
900impl<'a, 'b, T, S> BitAnd<&'b LinkedHashSet<T, S>> for &'a LinkedHashSet<T, S>
901where
902 T: Eq + Hash + Clone,
903 S: BuildHasher + Default,
904{
905 type Output = LinkedHashSet<T, S>;
906
907 /// Returns the intersection of `self` and `rhs` as a new `LinkedHashSet<T, S>`.
908 ///
909 /// # Examples
910 ///
911 /// ```
912 /// use linked_hash_set::LinkedHashSet;
913 ///
914 /// let a: LinkedHashSet<_> = vec![1, 2, 3].into_iter().collect();
915 /// let b: LinkedHashSet<_> = vec![2, 3, 4].into_iter().collect();
916 ///
917 /// let set = &a & &b;
918 ///
919 /// let mut i = 0;
920 /// let expected = [2, 3];
921 /// for x in &set {
922 /// assert!(expected.contains(x));
923 /// i += 1;
924 /// }
925 /// assert_eq!(i, expected.len());
926 /// ```
927 fn bitand(self, rhs: &LinkedHashSet<T, S>) -> LinkedHashSet<T, S> {
928 self.intersection(rhs).cloned().collect()
929 }
930}
931
932impl<'a, 'b, T, S> BitXor<&'b LinkedHashSet<T, S>> for &'a LinkedHashSet<T, S>
933where
934 T: Eq + Hash + Clone,
935 S: BuildHasher + Default,
936{
937 type Output = LinkedHashSet<T, S>;
938
939 /// Returns the symmetric difference of `self` and `rhs` as a new `LinkedHashSet<T, S>`.
940 ///
941 /// # Examples
942 ///
943 /// ```
944 /// use linked_hash_set::LinkedHashSet;
945 ///
946 /// let a: LinkedHashSet<_> = vec![1, 2, 3].into_iter().collect();
947 /// let b: LinkedHashSet<_> = vec![3, 4, 5].into_iter().collect();
948 ///
949 /// let set = &a ^ &b;
950 ///
951 /// let mut i = 0;
952 /// let expected = [1, 2, 4, 5];
953 /// for x in &set {
954 /// assert!(expected.contains(x));
955 /// i += 1;
956 /// }
957 /// assert_eq!(i, expected.len());
958 /// ```
959 fn bitxor(self, rhs: &LinkedHashSet<T, S>) -> LinkedHashSet<T, S> {
960 self.symmetric_difference(rhs).cloned().collect()
961 }
962}
963
964impl<'a, 'b, T, S> Sub<&'b LinkedHashSet<T, S>> for &'a LinkedHashSet<T, S>
965where
966 T: Eq + Hash + Clone,
967 S: BuildHasher + Default,
968{
969 type Output = LinkedHashSet<T, S>;
970
971 /// Returns the difference of `self` and `rhs` as a new `LinkedHashSet<T, S>`.
972 ///
973 /// # Examples
974 ///
975 /// ```
976 /// use linked_hash_set::LinkedHashSet;
977 ///
978 /// let a: LinkedHashSet<_> = vec![1, 2, 3].into_iter().collect();
979 /// let b: LinkedHashSet<_> = vec![3, 4, 5].into_iter().collect();
980 ///
981 /// let set = &a - &b;
982 ///
983 /// let mut i = 0;
984 /// let expected = [1, 2];
985 /// for x in &set {
986 /// assert!(expected.contains(x));
987 /// i += 1;
988 /// }
989 /// assert_eq!(i, expected.len());
990 /// ```
991 fn sub(self, rhs: &LinkedHashSet<T, S>) -> LinkedHashSet<T, S> {
992 self.difference(rhs).cloned().collect()
993 }
994}
995
996/// An iterator over the items of a `LinkedHashSet`.
997///
998/// This `struct` is created by the [`iter`] method on [`LinkedHashSet`].
999/// See its documentation for more.
1000/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1001/// [`iter`]: struct.LinkedHashSet.html#method.iter
1002pub struct Iter<'a, K> {
1003 iter: Keys<'a, K, ()>,
1004}
1005
1006/// An owning iterator over the items of a `LinkedHashSet`.
1007///
1008/// This `struct` is created by the [`into_iter`] method on [`LinkedHashSet`][`LinkedHashSet`]
1009/// (provided by the `IntoIterator` trait). See its documentation for more.
1010///
1011/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1012/// [`into_iter`]: struct.LinkedHashSet.html#method.into_iter
1013pub struct IntoIter<K> {
1014 iter: map::IntoIter<K, ()>,
1015}
1016
1017// TODO not in linked_hash_map
1018// /// A draining iterator over the items of a `LinkedHashSet`.
1019// ///
1020// /// This `struct` is created by the [`drain`] method on [`LinkedHashSet`].
1021// /// See its documentation for more.
1022// ///
1023// /// [`LinkedHashSet`]: struct.LinkedHashSet.html
1024// /// [`drain`]: struct.LinkedHashSet.html#method.drain
1025// pub struct Drain<'a, K: 'a> {
1026// iter: map::Drain<'a, K, ()>,
1027// }
1028
1029/// A lazy iterator producing elements in the intersection of `LinkedHashSet`s.
1030///
1031/// This `struct` is created by the [`intersection`] method on [`LinkedHashSet`].
1032/// See its documentation for more.
1033///
1034/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1035/// [`intersection`]: struct.LinkedHashSet.html#method.intersection
1036pub struct Intersection<'a, T, S> {
1037 // iterator of the first set
1038 iter: Iter<'a, T>,
1039 // the second set
1040 other: &'a LinkedHashSet<T, S>,
1041}
1042
1043/// A lazy iterator producing elements in the difference of `LinkedHashSet`s.
1044///
1045/// This `struct` is created by the [`difference`] method on [`LinkedHashSet`].
1046/// See its documentation for more.
1047///
1048/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1049/// [`difference`]: struct.LinkedHashSet.html#method.difference
1050pub struct Difference<'a, T, S> {
1051 // iterator of the first set
1052 iter: Iter<'a, T>,
1053 // the second set
1054 other: &'a LinkedHashSet<T, S>,
1055}
1056
1057/// A lazy iterator producing elements in the symmetric difference of `LinkedHashSet`s.
1058///
1059/// This `struct` is created by the [`symmetric_difference`] method on
1060/// [`LinkedHashSet`]. See its documentation for more.
1061///
1062/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1063/// [`symmetric_difference`]: struct.LinkedHashSet.html#method.symmetric_difference
1064pub struct SymmetricDifference<'a, T, S> {
1065 iter: Chain<Difference<'a, T, S>, Difference<'a, T, S>>,
1066}
1067
1068/// A lazy iterator producing elements in the union of `LinkedHashSet`s.
1069///
1070/// This `struct` is created by the [`union`] method on [`LinkedHashSet`].
1071/// See its documentation for more.
1072///
1073/// [`LinkedHashSet`]: struct.LinkedHashSet.html
1074/// [`union`]: struct.LinkedHashSet.html#method.union
1075pub struct Union<'a, T, S> {
1076 iter: Chain<Iter<'a, T>, Difference<'a, T, S>>,
1077}
1078
1079impl<'a, T, S> IntoIterator for &'a LinkedHashSet<T, S>
1080where
1081 T: Eq + Hash,
1082 S: BuildHasher,
1083{
1084 type Item = &'a T;
1085 type IntoIter = Iter<'a, T>;
1086
1087 fn into_iter(self) -> Iter<'a, T> {
1088 self.iter()
1089 }
1090}
1091
1092impl<T, S> IntoIterator for LinkedHashSet<T, S>
1093where
1094 T: Eq + Hash,
1095 S: BuildHasher,
1096{
1097 type Item = T;
1098 type IntoIter = IntoIter<T>;
1099
1100 /// Creates a consuming iterator, that is, one that moves each value out
1101 /// of the set in insertion order. The set cannot be used after calling
1102 /// this.
1103 ///
1104 /// # Examples
1105 ///
1106 /// ```
1107 /// use linked_hash_set::LinkedHashSet;
1108 /// let mut set = LinkedHashSet::new();
1109 /// set.insert("a".to_string());
1110 /// set.insert("b".to_string());
1111 ///
1112 /// // Not possible to collect to a Vec<String> with a regular `.iter()`.
1113 /// let v: Vec<String> = set.into_iter().collect();
1114 ///
1115 /// // Will print in an insertion order.
1116 /// for x in &v {
1117 /// println!("{}", x);
1118 /// }
1119 /// ```
1120 fn into_iter(self) -> IntoIter<T> {
1121 IntoIter {
1122 iter: self.map.into_iter(),
1123 }
1124 }
1125}
1126
1127impl<'a, K> Clone for Iter<'a, K> {
1128 fn clone(&self) -> Iter<'a, K> {
1129 Iter {
1130 iter: self.iter.clone(),
1131 }
1132 }
1133}
1134impl<'a, K> Iterator for Iter<'a, K> {
1135 type Item = &'a K;
1136
1137 fn next(&mut self) -> Option<&'a K> {
1138 self.iter.next()
1139 }
1140 fn size_hint(&self) -> (usize, Option<usize>) {
1141 self.iter.size_hint()
1142 }
1143}
1144impl<'a, K> ExactSizeIterator for Iter<'a, K> {
1145 fn len(&self) -> usize {
1146 self.iter.len()
1147 }
1148}
1149impl<'a, T> DoubleEndedIterator for Iter<'a, T> {
1150 fn next_back(&mut self) -> Option<&'a T> {
1151 self.iter.next_back()
1152 }
1153}
1154
1155impl<'a, K: fmt::Debug> fmt::Debug for Iter<'a, K> {
1156 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1157 f.debug_list().entries(self.clone()).finish()
1158 }
1159}
1160
1161impl<K> Iterator for IntoIter<K> {
1162 type Item = K;
1163
1164 fn next(&mut self) -> Option<K> {
1165 self.iter.next().map(|(k, _)| k)
1166 }
1167 fn size_hint(&self) -> (usize, Option<usize>) {
1168 self.iter.size_hint()
1169 }
1170}
1171impl<K> ExactSizeIterator for IntoIter<K> {
1172 fn len(&self) -> usize {
1173 self.iter.len()
1174 }
1175}
1176impl<K> DoubleEndedIterator for IntoIter<K> {
1177 fn next_back(&mut self) -> Option<K> {
1178 self.iter.next_back().map(|(k, _)| k)
1179 }
1180}
1181
1182// TODO Non-trivial port without private access to map
1183// impl<K: fmt::Debug> fmt::Debug for IntoIter<K> {
1184// fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1185// let entries_iter = self.iter
1186// .inner
1187// .iter()
1188// .map(|(k, _)| k);
1189// f.debug_list().entries(entries_iter).finish()
1190// }
1191// }
1192
1193// TODO not in linked_hash_map
1194// impl<'a, K> Iterator for Drain<'a, K> {
1195// type Item = K;
1196//
1197// fn next(&mut self) -> Option<K> {
1198// self.iter.next().map(|(k, _)| k)
1199// }
1200// fn size_hint(&self) -> (usize, Option<usize>) {
1201// self.iter.size_hint()
1202// }
1203// }
1204// impl<'a, K> ExactSizeIterator for Drain<'a, K> {
1205// fn len(&self) -> usize {
1206// self.iter.len()
1207// }
1208// }
1209//
1210// impl<'a, K: fmt::Debug> fmt::Debug for Drain<'a, K> {
1211// fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1212// let entries_iter = self.iter
1213// .inner
1214// .iter()
1215// .map(|(k, _)| k);
1216// f.debug_list().entries(entries_iter).finish()
1217// }
1218// }
1219
1220impl<'a, T, S> Clone for Intersection<'a, T, S> {
1221 fn clone(&self) -> Intersection<'a, T, S> {
1222 Intersection {
1223 iter: self.iter.clone(),
1224 ..*self
1225 }
1226 }
1227}
1228
1229impl<'a, T, S> Iterator for Intersection<'a, T, S>
1230where
1231 T: Eq + Hash,
1232 S: BuildHasher,
1233{
1234 type Item = &'a T;
1235
1236 fn next(&mut self) -> Option<&'a T> {
1237 loop {
1238 match self.iter.next() {
1239 None => return None,
1240 Some(elt) => {
1241 if self.other.contains(elt) {
1242 return Some(elt);
1243 }
1244 }
1245 }
1246 }
1247 }
1248
1249 fn size_hint(&self) -> (usize, Option<usize>) {
1250 let (_, upper) = self.iter.size_hint();
1251 (0, upper)
1252 }
1253}
1254
1255impl<'a, T, S> fmt::Debug for Intersection<'a, T, S>
1256where
1257 T: fmt::Debug + Eq + Hash,
1258 S: BuildHasher,
1259{
1260 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1261 f.debug_list().entries(self.clone()).finish()
1262 }
1263}
1264
1265impl<'a, T, S> Clone for Difference<'a, T, S> {
1266 fn clone(&self) -> Difference<'a, T, S> {
1267 Difference {
1268 iter: self.iter.clone(),
1269 ..*self
1270 }
1271 }
1272}
1273
1274impl<'a, T, S> Iterator for Difference<'a, T, S>
1275where
1276 T: Eq + Hash,
1277 S: BuildHasher,
1278{
1279 type Item = &'a T;
1280
1281 fn next(&mut self) -> Option<&'a T> {
1282 loop {
1283 match self.iter.next() {
1284 None => return None,
1285 Some(elt) => {
1286 if !self.other.contains(elt) {
1287 return Some(elt);
1288 }
1289 }
1290 }
1291 }
1292 }
1293
1294 fn size_hint(&self) -> (usize, Option<usize>) {
1295 let (_, upper) = self.iter.size_hint();
1296 (0, upper)
1297 }
1298}
1299
1300impl<'a, T, S> fmt::Debug for Difference<'a, T, S>
1301where
1302 T: fmt::Debug + Eq + Hash,
1303 S: BuildHasher,
1304{
1305 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1306 f.debug_list().entries(self.clone()).finish()
1307 }
1308}
1309
1310impl<'a, T, S> Clone for SymmetricDifference<'a, T, S> {
1311 fn clone(&self) -> SymmetricDifference<'a, T, S> {
1312 SymmetricDifference {
1313 iter: self.iter.clone(),
1314 }
1315 }
1316}
1317
1318impl<'a, T, S> Iterator for SymmetricDifference<'a, T, S>
1319where
1320 T: Eq + Hash,
1321 S: BuildHasher,
1322{
1323 type Item = &'a T;
1324
1325 fn next(&mut self) -> Option<&'a T> {
1326 self.iter.next()
1327 }
1328 fn size_hint(&self) -> (usize, Option<usize>) {
1329 self.iter.size_hint()
1330 }
1331}
1332
1333impl<'a, T, S> fmt::Debug for SymmetricDifference<'a, T, S>
1334where
1335 T: fmt::Debug + Eq + Hash,
1336 S: BuildHasher,
1337{
1338 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1339 f.debug_list().entries(self.clone()).finish()
1340 }
1341}
1342
1343impl<'a, T, S> Clone for Union<'a, T, S> {
1344 fn clone(&self) -> Union<'a, T, S> {
1345 Union {
1346 iter: self.iter.clone(),
1347 }
1348 }
1349}
1350
1351impl<'a, T, S> fmt::Debug for Union<'a, T, S>
1352where
1353 T: fmt::Debug + Eq + Hash,
1354 S: BuildHasher,
1355{
1356 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1357 f.debug_list().entries(self.clone()).finish()
1358 }
1359}
1360
1361impl<'a, T, S> Iterator for Union<'a, T, S>
1362where
1363 T: Eq + Hash,
1364 S: BuildHasher,
1365{
1366 type Item = &'a T;
1367
1368 fn next(&mut self) -> Option<&'a T> {
1369 self.iter.next()
1370 }
1371 fn size_hint(&self) -> (usize, Option<usize>) {
1372 self.iter.size_hint()
1373 }
1374}
1375
1376// TODO does not currently work like HashSet-HashMap with linked_hash_map
1377// #[allow(dead_code)]
1378// fn assert_covariance() {
1379// fn set<'new>(v: LinkedHashSet<&'static str>) -> LinkedHashSet<&'new str> {
1380// v
1381// }
1382// fn iter<'a, 'new>(v: Iter<'a, &'static str>) -> Iter<'a, &'new str> {
1383// v
1384// }
1385// fn into_iter<'new>(v: IntoIter<&'static str>) -> IntoIter<&'new str> {
1386// v
1387// }
1388// fn difference<'a, 'new>(v: Difference<'a, &'static str, RandomState>)
1389// -> Difference<'a, &'new str, RandomState> {
1390// v
1391// }
1392// fn symmetric_difference<'a, 'new>(v: SymmetricDifference<'a, &'static str, RandomState>)
1393// -> SymmetricDifference<'a, &'new str, RandomState> {
1394// v
1395// }
1396// fn intersection<'a, 'new>(v: Intersection<'a, &'static str, RandomState>)
1397// -> Intersection<'a, &'new str, RandomState> {
1398// v
1399// }
1400// fn union<'a, 'new>(v: Union<'a, &'static str, RandomState>)
1401// -> Union<'a, &'new str, RandomState> {
1402// v
1403// }
1404// fn drain<'new>(d: Drain<'static, &'static str>) -> Drain<'new, &'new str> {
1405// d
1406// }
1407// }
1408
1409// Tests in common with `HashSet`
1410#[cfg(test)]
1411mod test_set {
1412 use super::*;
1413
1414 #[test]
1415 fn test_zero_capacities() {
1416 type HS = LinkedHashSet<i32>;
1417
1418 let s = HS::new();
1419 assert_eq!(s.capacity(), 0);
1420
1421 let s = HS::default();
1422 assert_eq!(s.capacity(), 0);
1423
1424 let s = HS::with_hasher(RandomState::new());
1425 assert_eq!(s.capacity(), 0);
1426
1427 let s = HS::with_capacity(0);
1428 assert_eq!(s.capacity(), 0);
1429
1430 let s = HS::with_capacity_and_hasher(0, RandomState::new());
1431 assert_eq!(s.capacity(), 0);
1432
1433 let mut s = HS::new();
1434 s.insert(1);
1435 s.insert(2);
1436 s.remove(&1);
1437 s.remove(&2);
1438 s.shrink_to_fit();
1439 assert_eq!(s.capacity(), 0);
1440
1441 let mut s = HS::new();
1442 s.reserve(0);
1443 assert_eq!(s.capacity(), 0);
1444 }
1445
1446 #[test]
1447 fn test_disjoint() {
1448 let mut xs = LinkedHashSet::new();
1449 let mut ys = LinkedHashSet::new();
1450 assert!(xs.is_disjoint(&ys));
1451 assert!(ys.is_disjoint(&xs));
1452 assert!(xs.insert(5));
1453 assert!(ys.insert(11));
1454 assert!(xs.is_disjoint(&ys));
1455 assert!(ys.is_disjoint(&xs));
1456 assert!(xs.insert(7));
1457 assert!(xs.insert(19));
1458 assert!(xs.insert(4));
1459 assert!(ys.insert(2));
1460 assert!(ys.insert(-11));
1461 assert!(xs.is_disjoint(&ys));
1462 assert!(ys.is_disjoint(&xs));
1463 assert!(ys.insert(7));
1464 assert!(!xs.is_disjoint(&ys));
1465 assert!(!ys.is_disjoint(&xs));
1466 }
1467
1468 #[test]
1469 fn test_subset_and_superset() {
1470 let mut a = LinkedHashSet::new();
1471 assert!(a.insert(0));
1472 assert!(a.insert(5));
1473 assert!(a.insert(11));
1474 assert!(a.insert(7));
1475
1476 let mut b = LinkedHashSet::new();
1477 assert!(b.insert(0));
1478 assert!(b.insert(7));
1479 assert!(b.insert(19));
1480 assert!(b.insert(250));
1481 assert!(b.insert(11));
1482 assert!(b.insert(200));
1483
1484 assert!(!a.is_subset(&b));
1485 assert!(!a.is_superset(&b));
1486 assert!(!b.is_subset(&a));
1487 assert!(!b.is_superset(&a));
1488
1489 assert!(b.insert(5));
1490
1491 assert!(a.is_subset(&b));
1492 assert!(!a.is_superset(&b));
1493 assert!(!b.is_subset(&a));
1494 assert!(b.is_superset(&a));
1495 }
1496
1497 #[test]
1498 fn test_iterate() {
1499 let mut a = LinkedHashSet::new();
1500 for i in 0..32 {
1501 assert!(a.insert(i));
1502 }
1503 let mut observed: u32 = 0;
1504 for k in &a {
1505 observed |= 1 << *k;
1506 }
1507 assert_eq!(observed, 0xFFFF_FFFF);
1508 }
1509
1510 #[test]
1511 fn test_intersection() {
1512 let mut a = LinkedHashSet::new();
1513 let mut b = LinkedHashSet::new();
1514
1515 assert!(a.insert(11));
1516 assert!(a.insert(1));
1517 assert!(a.insert(3));
1518 assert!(a.insert(77));
1519 assert!(a.insert(103));
1520 assert!(a.insert(5));
1521 assert!(a.insert(-5));
1522
1523 assert!(b.insert(2));
1524 assert!(b.insert(11));
1525 assert!(b.insert(77));
1526 assert!(b.insert(-9));
1527 assert!(b.insert(-42));
1528 assert!(b.insert(5));
1529 assert!(b.insert(3));
1530
1531 let mut i = 0;
1532 let expected = [3, 5, 11, 77];
1533 for x in a.intersection(&b) {
1534 assert!(expected.contains(x));
1535 i += 1
1536 }
1537 assert_eq!(i, expected.len());
1538 }
1539
1540 #[test]
1541 fn test_difference() {
1542 let mut a = LinkedHashSet::new();
1543 let mut b = LinkedHashSet::new();
1544
1545 assert!(a.insert(1));
1546 assert!(a.insert(3));
1547 assert!(a.insert(5));
1548 assert!(a.insert(9));
1549 assert!(a.insert(11));
1550
1551 assert!(b.insert(3));
1552 assert!(b.insert(9));
1553
1554 let mut i = 0;
1555 let expected = [1, 5, 11];
1556 for x in a.difference(&b) {
1557 assert!(expected.contains(x));
1558 i += 1
1559 }
1560 assert_eq!(i, expected.len());
1561 }
1562
1563 #[test]
1564 fn test_symmetric_difference() {
1565 let mut a = LinkedHashSet::new();
1566 let mut b = LinkedHashSet::new();
1567
1568 assert!(a.insert(1));
1569 assert!(a.insert(3));
1570 assert!(a.insert(5));
1571 assert!(a.insert(9));
1572 assert!(a.insert(11));
1573
1574 assert!(b.insert(-2));
1575 assert!(b.insert(3));
1576 assert!(b.insert(9));
1577 assert!(b.insert(14));
1578 assert!(b.insert(22));
1579
1580 let mut i = 0;
1581 let expected = [-2, 1, 5, 11, 14, 22];
1582 for x in a.symmetric_difference(&b) {
1583 assert!(expected.contains(x));
1584 i += 1
1585 }
1586 assert_eq!(i, expected.len());
1587 }
1588
1589 #[test]
1590 fn test_union() {
1591 let mut a = LinkedHashSet::new();
1592 let mut b = LinkedHashSet::new();
1593
1594 assert!(a.insert(1));
1595 assert!(a.insert(3));
1596 assert!(a.insert(5));
1597 assert!(a.insert(9));
1598 assert!(a.insert(11));
1599 assert!(a.insert(16));
1600 assert!(a.insert(19));
1601 assert!(a.insert(24));
1602
1603 assert!(b.insert(-2));
1604 assert!(b.insert(1));
1605 assert!(b.insert(5));
1606 assert!(b.insert(9));
1607 assert!(b.insert(13));
1608 assert!(b.insert(19));
1609
1610 let mut i = 0;
1611 let expected = [-2, 1, 3, 5, 9, 11, 13, 16, 19, 24];
1612 for x in a.union(&b) {
1613 assert!(expected.contains(x));
1614 i += 1
1615 }
1616 assert_eq!(i, expected.len());
1617 }
1618
1619 #[test]
1620 fn test_from_iter() {
1621 let xs = [1, 2, 3, 4, 5, 6, 7, 8, 9];
1622
1623 let set: LinkedHashSet<_> = xs.iter().cloned().collect();
1624
1625 for x in &xs {
1626 assert!(set.contains(x));
1627 }
1628 }
1629
1630 #[test]
1631 fn test_move_iter() {
1632 let hs = {
1633 let mut hs = LinkedHashSet::new();
1634
1635 hs.insert('a');
1636 hs.insert('b');
1637
1638 hs
1639 };
1640
1641 let v = hs.into_iter().collect::<Vec<char>>();
1642 assert!(v == ['a', 'b'] || v == ['b', 'a']);
1643 }
1644
1645 #[test]
1646 fn test_eq() {
1647 // These constants once happened to expose a bug in insert().
1648 // I'm keeping them around to prevent a regression.
1649 let mut s1 = LinkedHashSet::new();
1650
1651 s1.insert(1);
1652 s1.insert(2);
1653 s1.insert(3);
1654
1655 let mut s2 = LinkedHashSet::new();
1656
1657 s2.insert(1);
1658 s2.insert(2);
1659
1660 assert!(s1 != s2);
1661
1662 s2.insert(3);
1663
1664 assert_eq!(s1, s2);
1665 }
1666
1667 #[test]
1668 fn test_show() {
1669 let mut set = LinkedHashSet::new();
1670 let empty = LinkedHashSet::<i32>::new();
1671
1672 set.insert(1);
1673 set.insert(2);
1674
1675 let set_str = format!("{:?}", set);
1676
1677 assert!(set_str == "{1, 2}" || set_str == "{2, 1}");
1678 assert_eq!(format!("{:?}", empty), "{}");
1679 }
1680
1681 // #[test]
1682 // fn test_trivial_drain() {
1683 // let mut s = LinkedHashSet::<i32>::new();
1684 // for _ in s.drain() {}
1685 // assert!(s.is_empty());
1686 // drop(s);
1687 //
1688 // let mut s = LinkedHashSet::<i32>::new();
1689 // drop(s.drain());
1690 // assert!(s.is_empty());
1691 // }
1692
1693 // #[test]
1694 // fn test_drain() {
1695 // let mut s: LinkedHashSet<_> = (1..100).collect();
1696 //
1697 // // try this a bunch of times to make sure we don't screw up internal state.
1698 // for _ in 0..20 {
1699 // assert_eq!(s.len(), 99);
1700 //
1701 // {
1702 // let mut last_i = 0;
1703 // let mut d = s.drain();
1704 // for (i, x) in d.by_ref().take(50).enumerate() {
1705 // last_i = i;
1706 // assert!(x != 0);
1707 // }
1708 // assert_eq!(last_i, 49);
1709 // }
1710 //
1711 // for _ in &s {
1712 // panic!("s should be empty!");
1713 // }
1714 //
1715 // // reset to try again.
1716 // s.extend(1..100);
1717 // }
1718 // }
1719
1720 // #[test]
1721 // fn test_replace() {
1722 // use std::hash;
1723 //
1724 // #[derive(Debug)]
1725 // struct Foo(&'static str, i32);
1726 //
1727 // impl PartialEq for Foo {
1728 // fn eq(&self, other: &Self) -> bool {
1729 // self.0 == other.0
1730 // }
1731 // }
1732 //
1733 // impl Eq for Foo {}
1734 //
1735 // impl hash::Hash for Foo {
1736 // fn hash<H: hash::Hasher>(&self, h: &mut H) {
1737 // self.0.hash(h);
1738 // }
1739 // }
1740 //
1741 // let mut s = LinkedHashSet::new();
1742 // assert_eq!(s.replace(Foo("a", 1)), None);
1743 // assert_eq!(s.len(), 1);
1744 // assert_eq!(s.replace(Foo("a", 2)), Some(Foo("a", 1)));
1745 // assert_eq!(s.len(), 1);
1746 //
1747 // let mut it = s.iter();
1748 // assert_eq!(it.next(), Some(&Foo("a", 2)));
1749 // assert_eq!(it.next(), None);
1750 // }
1751
1752 #[test]
1753 fn test_extend_ref() {
1754 let mut a = LinkedHashSet::new();
1755 a.insert(1);
1756
1757 a.extend(&[2, 3, 4]);
1758
1759 assert_eq!(a.len(), 4);
1760 assert!(a.contains(&1));
1761 assert!(a.contains(&2));
1762 assert!(a.contains(&3));
1763 assert!(a.contains(&4));
1764
1765 let mut b = LinkedHashSet::new();
1766 b.insert(5);
1767 b.insert(6);
1768
1769 a.extend(&b);
1770
1771 assert_eq!(a.len(), 6);
1772 assert!(a.contains(&1));
1773 assert!(a.contains(&2));
1774 assert!(a.contains(&3));
1775 assert!(a.contains(&4));
1776 assert!(a.contains(&5));
1777 assert!(a.contains(&6));
1778 }
1779
1780 // #[test]
1781 // fn test_retain() {
1782 // let xs = [1, 2, 3, 4, 5, 6];
1783 // let mut set: LinkedHashSet<isize> = xs.iter().cloned().collect();
1784 // set.retain(|&k| k % 2 == 0);
1785 // assert_eq!(set.len(), 3);
1786 // assert!(set.contains(&2));
1787 // assert!(set.contains(&4));
1788 // assert!(set.contains(&6));
1789 // }
1790}
1791
1792// Tests for `LinkedHashSet` functionality over `HashSet`
1793#[cfg(test)]
1794mod test_linked {
1795 use super::*;
1796
1797 macro_rules! set {
1798 ($($el:expr),*) => {{
1799 let mut set = LinkedHashSet::new();
1800 $(
1801 set.insert($el);
1802 )*
1803 set
1804 }}
1805 }
1806
1807 #[test]
1808 fn order_is_maintained() {
1809 let set = set![123, 234, 56, 677];
1810 assert_eq!(set.into_iter().collect::<Vec<_>>(), vec![123, 234, 56, 677]);
1811 }
1812
1813 #[test]
1814 fn clone_order_is_maintained() {
1815 let set = set![123, 234, 56, 677];
1816 assert_eq!(
1817 set.clone().into_iter().collect::<Vec<_>>(),
1818 vec![123, 234, 56, 677]
1819 );
1820 }
1821
1822 #[test]
1823 fn delegate_front() {
1824 let set = set![123, 234, 56, 677];
1825 assert_eq!(set.front(), Some(&123));
1826 }
1827
1828 #[test]
1829 fn delegate_pop_front() {
1830 let mut set = set![123, 234, 56, 677];
1831 assert_eq!(set.pop_front(), Some(123));
1832 assert_eq!(set.into_iter().collect::<Vec<_>>(), vec![234, 56, 677]);
1833 }
1834
1835 #[test]
1836 fn delegate_back() {
1837 let mut set = set![123, 234, 56, 677];
1838 assert_eq!(set.back(), Some(&677));
1839 }
1840
1841 #[test]
1842 fn delegate_pop_back() {
1843 let mut set = set![123, 234, 56, 677];
1844 assert_eq!(set.pop_back(), Some(677));
1845 assert_eq!(set.into_iter().collect::<Vec<_>>(), vec![123, 234, 56]);
1846 }
1847
1848 #[test]
1849 fn double_ended_iter() {
1850 let set = set![123, 234, 56, 677];
1851 let mut iter = set.iter();
1852
1853 assert_eq!(iter.next(), Some(&123));
1854 assert_eq!(iter.next(), Some(&234));
1855 assert_eq!(iter.next_back(), Some(&677));
1856 assert_eq!(iter.next_back(), Some(&56));
1857
1858 assert_eq!(iter.next(), None);
1859 assert_eq!(iter.next_back(), None);
1860 }
1861
1862 #[test]
1863 fn double_ended_into_iter() {
1864 let mut iter = set![123, 234, 56, 677].into_iter();
1865
1866 assert_eq!(iter.next(), Some(123));
1867 assert_eq!(iter.next_back(), Some(677));
1868 assert_eq!(iter.next_back(), Some(56));
1869 assert_eq!(iter.next_back(), Some(234));
1870
1871 assert_eq!(iter.next(), None);
1872 assert_eq!(iter.next_back(), None);
1873 }
1874}