std/collections/hash/set.rs
1#[cfg(test)]
2mod tests;
3
4use hashbrown::hash_set as base;
5
6use super::map::map_try_reserve_error;
7use crate::borrow::Borrow;
8use crate::collections::TryReserveError;
9use crate::fmt;
10use crate::hash::{BuildHasher, Hash, RandomState};
11use crate::iter::{Chain, FusedIterator};
12use crate::ops::{BitAnd, BitOr, BitXor, Sub};
13
14/// A [hash set] implemented as a `HashMap` where the value is `()`.
15///
16/// As with the [`HashMap`] type, a `HashSet` requires that the elements
17/// implement the [`Eq`] and [`Hash`] traits. This can frequently be achieved by
18/// using `#[derive(PartialEq, Eq, Hash)]`. If you implement these yourself,
19/// it is important that the following property holds:
20///
21/// ```text
22/// k1 == k2 -> hash(k1) == hash(k2)
23/// ```
24///
25/// In other words, if two keys are equal, their hashes must be equal.
26/// Violating this property is a logic error.
27///
28/// It is also a logic error for a key to be modified in such a way that the key's
29/// hash, as determined by the [`Hash`] trait, or its equality, as determined by
30/// the [`Eq`] trait, changes while it is in the map. This is normally only
31/// possible through [`Cell`], [`RefCell`], global state, I/O, or unsafe code.
32///
33/// The behavior resulting from either logic error is not specified, but will
34/// be encapsulated to the `HashSet` that observed the logic error and not
35/// result in undefined behavior. This could include panics, incorrect results,
36/// aborts, memory leaks, and non-termination.
37///
38/// # Examples
39///
40/// ```
41/// use std::collections::HashSet;
42/// // Type inference lets us omit an explicit type signature (which
43/// // would be `HashSet<String>` in this example).
44/// let mut books = HashSet::new();
45///
46/// // Add some books.
47/// books.insert("A Dance With Dragons".to_string());
48/// books.insert("To Kill a Mockingbird".to_string());
49/// books.insert("The Odyssey".to_string());
50/// books.insert("The Great Gatsby".to_string());
51///
52/// // Check for a specific one.
53/// if !books.contains("The Winds of Winter") {
54/// println!("We have {} books, but The Winds of Winter ain't one.",
55/// books.len());
56/// }
57///
58/// // Remove a book.
59/// books.remove("The Odyssey");
60///
61/// // Iterate over everything.
62/// for book in &books {
63/// println!("{book}");
64/// }
65/// ```
66///
67/// The easiest way to use `HashSet` with a custom type is to derive
68/// [`Eq`] and [`Hash`]. We must also derive [`PartialEq`],
69/// which is required if [`Eq`] is derived.
70///
71/// ```
72/// use std::collections::HashSet;
73/// #[derive(Hash, Eq, PartialEq, Debug)]
74/// struct Viking {
75/// name: String,
76/// power: usize,
77/// }
78///
79/// let mut vikings = HashSet::new();
80///
81/// vikings.insert(Viking { name: "Einar".to_string(), power: 9 });
82/// vikings.insert(Viking { name: "Einar".to_string(), power: 9 });
83/// vikings.insert(Viking { name: "Olaf".to_string(), power: 4 });
84/// vikings.insert(Viking { name: "Harald".to_string(), power: 8 });
85///
86/// // Use derived implementation to print the vikings.
87/// for x in &vikings {
88/// println!("{x:?}");
89/// }
90/// ```
91///
92/// A `HashSet` with a known list of items can be initialized from an array:
93///
94/// ```
95/// use std::collections::HashSet;
96///
97/// let viking_names = HashSet::from(["Einar", "Olaf", "Harald"]);
98/// ```
99///
100/// [hash set]: crate::collections#use-the-set-variant-of-any-of-these-maps-when
101/// [`HashMap`]: crate::collections::HashMap
102/// [`RefCell`]: crate::cell::RefCell
103/// [`Cell`]: crate::cell::Cell
104///
105/// # Usage in `const` and `static`
106///
107/// Like `HashMap`, `HashSet` is randomly seeded: each `HashSet` instance uses a different seed,
108/// which means that `HashSet::new` cannot be used in const context. To construct a `HashSet` in the
109/// initializer of a `const` or `static` item, you will have to use a different hasher that does not
110/// involve a random seed, as demonstrated in the following example. **A `HashSet` constructed this
111/// way is not resistant against HashDoS!**
112///
113/// ```rust
114/// use std::collections::HashSet;
115/// use std::hash::{BuildHasherDefault, DefaultHasher};
116/// use std::sync::Mutex;
117///
118/// const EMPTY_SET: HashSet<String, BuildHasherDefault<DefaultHasher>> =
119/// HashSet::with_hasher(BuildHasherDefault::new());
120/// static SET: Mutex<HashSet<String, BuildHasherDefault<DefaultHasher>>> =
121/// Mutex::new(HashSet::with_hasher(BuildHasherDefault::new()));
122/// ```
123#[cfg_attr(not(test), rustc_diagnostic_item = "HashSet")]
124#[stable(feature = "rust1", since = "1.0.0")]
125pub struct HashSet<T, S = RandomState> {
126 base: base::HashSet<T, S>,
127}
128
129impl<T> HashSet<T, RandomState> {
130 /// Creates an empty `HashSet`.
131 ///
132 /// The hash set is initially created with a capacity of 0, so it will not allocate until it
133 /// is first inserted into.
134 ///
135 /// # Examples
136 ///
137 /// ```
138 /// use std::collections::HashSet;
139 /// let set: HashSet<i32> = HashSet::new();
140 /// ```
141 #[inline]
142 #[must_use]
143 #[stable(feature = "rust1", since = "1.0.0")]
144 pub fn new() -> HashSet<T, RandomState> {
145 Default::default()
146 }
147
148 /// Creates an empty `HashSet` with at least the specified capacity.
149 ///
150 /// The hash set will be able to hold at least `capacity` elements without
151 /// reallocating. This method is allowed to allocate for more elements than
152 /// `capacity`. If `capacity` is zero, the hash set will not allocate.
153 ///
154 /// # Examples
155 ///
156 /// ```
157 /// use std::collections::HashSet;
158 /// let set: HashSet<i32> = HashSet::with_capacity(10);
159 /// assert!(set.capacity() >= 10);
160 /// ```
161 #[inline]
162 #[must_use]
163 #[stable(feature = "rust1", since = "1.0.0")]
164 pub fn with_capacity(capacity: usize) -> HashSet<T, RandomState> {
165 HashSet::with_capacity_and_hasher(capacity, Default::default())
166 }
167}
168
169impl<T, S> HashSet<T, S> {
170 /// Returns the number of elements the set can hold without reallocating.
171 ///
172 /// # Examples
173 ///
174 /// ```
175 /// use std::collections::HashSet;
176 /// let set: HashSet<i32> = HashSet::with_capacity(100);
177 /// assert!(set.capacity() >= 100);
178 /// ```
179 #[inline]
180 #[stable(feature = "rust1", since = "1.0.0")]
181 pub fn capacity(&self) -> usize {
182 self.base.capacity()
183 }
184
185 /// An iterator visiting all elements in arbitrary order.
186 /// The iterator element type is `&'a T`.
187 ///
188 /// # Examples
189 ///
190 /// ```
191 /// use std::collections::HashSet;
192 /// let mut set = HashSet::new();
193 /// set.insert("a");
194 /// set.insert("b");
195 ///
196 /// // Will print in an arbitrary order.
197 /// for x in set.iter() {
198 /// println!("{x}");
199 /// }
200 /// ```
201 ///
202 /// # Performance
203 ///
204 /// In the current implementation, iterating over set takes O(capacity) time
205 /// instead of O(len) because it internally visits empty buckets too.
206 #[inline]
207 #[rustc_lint_query_instability]
208 #[stable(feature = "rust1", since = "1.0.0")]
209 #[cfg_attr(not(test), rustc_diagnostic_item = "hashset_iter")]
210 pub fn iter(&self) -> Iter<'_, T> {
211 Iter { base: self.base.iter() }
212 }
213
214 /// Returns the number of elements in the set.
215 ///
216 /// # Examples
217 ///
218 /// ```
219 /// use std::collections::HashSet;
220 ///
221 /// let mut v = HashSet::new();
222 /// assert_eq!(v.len(), 0);
223 /// v.insert(1);
224 /// assert_eq!(v.len(), 1);
225 /// ```
226 #[inline]
227 #[stable(feature = "rust1", since = "1.0.0")]
228 pub fn len(&self) -> usize {
229 self.base.len()
230 }
231
232 /// Returns `true` if the set contains no elements.
233 ///
234 /// # Examples
235 ///
236 /// ```
237 /// use std::collections::HashSet;
238 ///
239 /// let mut v = HashSet::new();
240 /// assert!(v.is_empty());
241 /// v.insert(1);
242 /// assert!(!v.is_empty());
243 /// ```
244 #[inline]
245 #[stable(feature = "rust1", since = "1.0.0")]
246 pub fn is_empty(&self) -> bool {
247 self.base.is_empty()
248 }
249
250 /// Clears the set, returning all elements as an iterator. Keeps the
251 /// allocated memory for reuse.
252 ///
253 /// If the returned iterator is dropped before being fully consumed, it
254 /// drops the remaining elements. The returned iterator keeps a mutable
255 /// borrow on the set to optimize its implementation.
256 ///
257 /// # Examples
258 ///
259 /// ```
260 /// use std::collections::HashSet;
261 ///
262 /// let mut set = HashSet::from([1, 2, 3]);
263 /// assert!(!set.is_empty());
264 ///
265 /// // print 1, 2, 3 in an arbitrary order
266 /// for i in set.drain() {
267 /// println!("{i}");
268 /// }
269 ///
270 /// assert!(set.is_empty());
271 /// ```
272 #[inline]
273 #[rustc_lint_query_instability]
274 #[stable(feature = "drain", since = "1.6.0")]
275 pub fn drain(&mut self) -> Drain<'_, T> {
276 Drain { base: self.base.drain() }
277 }
278
279 /// Creates an iterator which uses a closure to determine if a value should be removed.
280 ///
281 /// If the closure returns true, then the value is removed and yielded.
282 /// If the closure returns false, the value will remain in the list and will not be yielded
283 /// by the iterator.
284 ///
285 /// If the returned `ExtractIf` is not exhausted, e.g. because it is dropped without iterating
286 /// or the iteration short-circuits, then the remaining elements will be retained.
287 /// Use [`retain`] with a negated predicate if you do not need the returned iterator.
288 ///
289 /// [`retain`]: HashSet::retain
290 ///
291 /// # Examples
292 ///
293 /// Splitting a set into even and odd values, reusing the original set:
294 ///
295 /// ```
296 /// use std::collections::HashSet;
297 ///
298 /// let mut set: HashSet<i32> = (0..8).collect();
299 /// let extracted: HashSet<i32> = set.extract_if(|v| v % 2 == 0).collect();
300 ///
301 /// let mut evens = extracted.into_iter().collect::<Vec<_>>();
302 /// let mut odds = set.into_iter().collect::<Vec<_>>();
303 /// evens.sort();
304 /// odds.sort();
305 ///
306 /// assert_eq!(evens, vec![0, 2, 4, 6]);
307 /// assert_eq!(odds, vec![1, 3, 5, 7]);
308 /// ```
309 #[inline]
310 #[rustc_lint_query_instability]
311 #[stable(feature = "hash_extract_if", since = "CURRENT_RUSTC_VERSION")]
312 pub fn extract_if<F>(&mut self, pred: F) -> ExtractIf<'_, T, F>
313 where
314 F: FnMut(&T) -> bool,
315 {
316 ExtractIf { base: self.base.extract_if(pred) }
317 }
318
319 /// Retains only the elements specified by the predicate.
320 ///
321 /// In other words, remove all elements `e` for which `f(&e)` returns `false`.
322 /// The elements are visited in unsorted (and unspecified) order.
323 ///
324 /// # Examples
325 ///
326 /// ```
327 /// use std::collections::HashSet;
328 ///
329 /// let mut set = HashSet::from([1, 2, 3, 4, 5, 6]);
330 /// set.retain(|&k| k % 2 == 0);
331 /// assert_eq!(set, HashSet::from([2, 4, 6]));
332 /// ```
333 ///
334 /// # Performance
335 ///
336 /// In the current implementation, this operation takes O(capacity) time
337 /// instead of O(len) because it internally visits empty buckets too.
338 #[rustc_lint_query_instability]
339 #[stable(feature = "retain_hash_collection", since = "1.18.0")]
340 pub fn retain<F>(&mut self, f: F)
341 where
342 F: FnMut(&T) -> bool,
343 {
344 self.base.retain(f)
345 }
346
347 /// Clears the set, removing all values.
348 ///
349 /// # Examples
350 ///
351 /// ```
352 /// use std::collections::HashSet;
353 ///
354 /// let mut v = HashSet::new();
355 /// v.insert(1);
356 /// v.clear();
357 /// assert!(v.is_empty());
358 /// ```
359 #[inline]
360 #[stable(feature = "rust1", since = "1.0.0")]
361 pub fn clear(&mut self) {
362 self.base.clear()
363 }
364
365 /// Creates a new empty hash set which will use the given hasher to hash
366 /// keys.
367 ///
368 /// The hash set is also created with the default initial capacity.
369 ///
370 /// Warning: `hasher` is normally randomly generated, and
371 /// is designed to allow `HashSet`s to be resistant to attacks that
372 /// cause many collisions and very poor performance. Setting it
373 /// manually using this function can expose a DoS attack vector.
374 ///
375 /// The `hash_builder` passed should implement the [`BuildHasher`] trait for
376 /// the `HashSet` to be useful, see its documentation for details.
377 ///
378 /// # Examples
379 ///
380 /// ```
381 /// use std::collections::HashSet;
382 /// use std::hash::RandomState;
383 ///
384 /// let s = RandomState::new();
385 /// let mut set = HashSet::with_hasher(s);
386 /// set.insert(2);
387 /// ```
388 #[inline]
389 #[stable(feature = "hashmap_build_hasher", since = "1.7.0")]
390 #[rustc_const_stable(feature = "const_collections_with_hasher", since = "1.85.0")]
391 pub const fn with_hasher(hasher: S) -> HashSet<T, S> {
392 HashSet { base: base::HashSet::with_hasher(hasher) }
393 }
394
395 /// Creates an empty `HashSet` with at least the specified capacity, using
396 /// `hasher` to hash the keys.
397 ///
398 /// The hash set will be able to hold at least `capacity` elements without
399 /// reallocating. This method is allowed to allocate for more elements than
400 /// `capacity`. If `capacity` is zero, the hash set will not allocate.
401 ///
402 /// Warning: `hasher` is normally randomly generated, and
403 /// is designed to allow `HashSet`s to be resistant to attacks that
404 /// cause many collisions and very poor performance. Setting it
405 /// manually using this function can expose a DoS attack vector.
406 ///
407 /// The `hash_builder` passed should implement the [`BuildHasher`] trait for
408 /// the `HashSet` to be useful, see its documentation for details.
409 ///
410 /// # Examples
411 ///
412 /// ```
413 /// use std::collections::HashSet;
414 /// use std::hash::RandomState;
415 ///
416 /// let s = RandomState::new();
417 /// let mut set = HashSet::with_capacity_and_hasher(10, s);
418 /// set.insert(1);
419 /// ```
420 #[inline]
421 #[stable(feature = "hashmap_build_hasher", since = "1.7.0")]
422 pub fn with_capacity_and_hasher(capacity: usize, hasher: S) -> HashSet<T, S> {
423 HashSet { base: base::HashSet::with_capacity_and_hasher(capacity, hasher) }
424 }
425
426 /// Returns a reference to the set's [`BuildHasher`].
427 ///
428 /// # Examples
429 ///
430 /// ```
431 /// use std::collections::HashSet;
432 /// use std::hash::RandomState;
433 ///
434 /// let hasher = RandomState::new();
435 /// let set: HashSet<i32> = HashSet::with_hasher(hasher);
436 /// let hasher: &RandomState = set.hasher();
437 /// ```
438 #[inline]
439 #[stable(feature = "hashmap_public_hasher", since = "1.9.0")]
440 pub fn hasher(&self) -> &S {
441 self.base.hasher()
442 }
443}
444
445impl<T, S> HashSet<T, S>
446where
447 T: Eq + Hash,
448 S: BuildHasher,
449{
450 /// Reserves capacity for at least `additional` more elements to be inserted
451 /// in the `HashSet`. The collection may reserve more space to speculatively
452 /// avoid frequent reallocations. After calling `reserve`,
453 /// capacity will be greater than or equal to `self.len() + additional`.
454 /// Does nothing if capacity is already sufficient.
455 ///
456 /// # Panics
457 ///
458 /// Panics if the new allocation size overflows `usize`.
459 ///
460 /// # Examples
461 ///
462 /// ```
463 /// use std::collections::HashSet;
464 /// let mut set: HashSet<i32> = HashSet::new();
465 /// set.reserve(10);
466 /// assert!(set.capacity() >= 10);
467 /// ```
468 #[inline]
469 #[stable(feature = "rust1", since = "1.0.0")]
470 pub fn reserve(&mut self, additional: usize) {
471 self.base.reserve(additional)
472 }
473
474 /// Tries to reserve capacity for at least `additional` more elements to be inserted
475 /// in the `HashSet`. The collection may reserve more space to speculatively
476 /// avoid frequent reallocations. After calling `try_reserve`,
477 /// capacity will be greater than or equal to `self.len() + additional` if
478 /// it returns `Ok(())`.
479 /// Does nothing if capacity is already sufficient.
480 ///
481 /// # Errors
482 ///
483 /// If the capacity overflows, or the allocator reports a failure, then an error
484 /// is returned.
485 ///
486 /// # Examples
487 ///
488 /// ```
489 /// use std::collections::HashSet;
490 /// let mut set: HashSet<i32> = HashSet::new();
491 /// set.try_reserve(10).expect("why is the test harness OOMing on a handful of bytes?");
492 /// ```
493 #[inline]
494 #[stable(feature = "try_reserve", since = "1.57.0")]
495 pub fn try_reserve(&mut self, additional: usize) -> Result<(), TryReserveError> {
496 self.base.try_reserve(additional).map_err(map_try_reserve_error)
497 }
498
499 /// Shrinks the capacity of the set as much as possible. It will drop
500 /// down as much as possible while maintaining the internal rules
501 /// and possibly leaving some space in accordance with the resize policy.
502 ///
503 /// # Examples
504 ///
505 /// ```
506 /// use std::collections::HashSet;
507 ///
508 /// let mut set = HashSet::with_capacity(100);
509 /// set.insert(1);
510 /// set.insert(2);
511 /// assert!(set.capacity() >= 100);
512 /// set.shrink_to_fit();
513 /// assert!(set.capacity() >= 2);
514 /// ```
515 #[inline]
516 #[stable(feature = "rust1", since = "1.0.0")]
517 pub fn shrink_to_fit(&mut self) {
518 self.base.shrink_to_fit()
519 }
520
521 /// Shrinks the capacity of the set with a lower limit. It will drop
522 /// down no lower than the supplied limit while maintaining the internal rules
523 /// and possibly leaving some space in accordance with the resize policy.
524 ///
525 /// If the current capacity is less than the lower limit, this is a no-op.
526 /// # Examples
527 ///
528 /// ```
529 /// use std::collections::HashSet;
530 ///
531 /// let mut set = HashSet::with_capacity(100);
532 /// set.insert(1);
533 /// set.insert(2);
534 /// assert!(set.capacity() >= 100);
535 /// set.shrink_to(10);
536 /// assert!(set.capacity() >= 10);
537 /// set.shrink_to(0);
538 /// assert!(set.capacity() >= 2);
539 /// ```
540 #[inline]
541 #[stable(feature = "shrink_to", since = "1.56.0")]
542 pub fn shrink_to(&mut self, min_capacity: usize) {
543 self.base.shrink_to(min_capacity)
544 }
545
546 /// Visits the values representing the difference,
547 /// i.e., the values that are in `self` but not in `other`.
548 ///
549 /// # Examples
550 ///
551 /// ```
552 /// use std::collections::HashSet;
553 /// let a = HashSet::from([1, 2, 3]);
554 /// let b = HashSet::from([4, 2, 3, 4]);
555 ///
556 /// // Can be seen as `a - b`.
557 /// for x in a.difference(&b) {
558 /// println!("{x}"); // Print 1
559 /// }
560 ///
561 /// let diff: HashSet<_> = a.difference(&b).collect();
562 /// assert_eq!(diff, [1].iter().collect());
563 ///
564 /// // Note that difference is not symmetric,
565 /// // and `b - a` means something else:
566 /// let diff: HashSet<_> = b.difference(&a).collect();
567 /// assert_eq!(diff, [4].iter().collect());
568 /// ```
569 #[inline]
570 #[rustc_lint_query_instability]
571 #[stable(feature = "rust1", since = "1.0.0")]
572 pub fn difference<'a>(&'a self, other: &'a HashSet<T, S>) -> Difference<'a, T, S> {
573 Difference { iter: self.iter(), other }
574 }
575
576 /// Visits the values representing the symmetric difference,
577 /// i.e., the values that are in `self` or in `other` but not in both.
578 ///
579 /// # Examples
580 ///
581 /// ```
582 /// use std::collections::HashSet;
583 /// let a = HashSet::from([1, 2, 3]);
584 /// let b = HashSet::from([4, 2, 3, 4]);
585 ///
586 /// // Print 1, 4 in arbitrary order.
587 /// for x in a.symmetric_difference(&b) {
588 /// println!("{x}");
589 /// }
590 ///
591 /// let diff1: HashSet<_> = a.symmetric_difference(&b).collect();
592 /// let diff2: HashSet<_> = b.symmetric_difference(&a).collect();
593 ///
594 /// assert_eq!(diff1, diff2);
595 /// assert_eq!(diff1, [1, 4].iter().collect());
596 /// ```
597 #[inline]
598 #[rustc_lint_query_instability]
599 #[stable(feature = "rust1", since = "1.0.0")]
600 pub fn symmetric_difference<'a>(
601 &'a self,
602 other: &'a HashSet<T, S>,
603 ) -> SymmetricDifference<'a, T, S> {
604 SymmetricDifference { iter: self.difference(other).chain(other.difference(self)) }
605 }
606
607 /// Visits the values representing the intersection,
608 /// i.e., the values that are both in `self` and `other`.
609 ///
610 /// When an equal element is present in `self` and `other`
611 /// then the resulting `Intersection` may yield references to
612 /// one or the other. This can be relevant if `T` contains fields which
613 /// are not compared by its `Eq` implementation, and may hold different
614 /// value between the two equal copies of `T` in the two sets.
615 ///
616 /// # Examples
617 ///
618 /// ```
619 /// use std::collections::HashSet;
620 /// let a = HashSet::from([1, 2, 3]);
621 /// let b = HashSet::from([4, 2, 3, 4]);
622 ///
623 /// // Print 2, 3 in arbitrary order.
624 /// for x in a.intersection(&b) {
625 /// println!("{x}");
626 /// }
627 ///
628 /// let intersection: HashSet<_> = a.intersection(&b).collect();
629 /// assert_eq!(intersection, [2, 3].iter().collect());
630 /// ```
631 #[inline]
632 #[rustc_lint_query_instability]
633 #[stable(feature = "rust1", since = "1.0.0")]
634 pub fn intersection<'a>(&'a self, other: &'a HashSet<T, S>) -> Intersection<'a, T, S> {
635 if self.len() <= other.len() {
636 Intersection { iter: self.iter(), other }
637 } else {
638 Intersection { iter: other.iter(), other: self }
639 }
640 }
641
642 /// Visits the values representing the union,
643 /// i.e., all the values in `self` or `other`, without duplicates.
644 ///
645 /// # Examples
646 ///
647 /// ```
648 /// use std::collections::HashSet;
649 /// let a = HashSet::from([1, 2, 3]);
650 /// let b = HashSet::from([4, 2, 3, 4]);
651 ///
652 /// // Print 1, 2, 3, 4 in arbitrary order.
653 /// for x in a.union(&b) {
654 /// println!("{x}");
655 /// }
656 ///
657 /// let union: HashSet<_> = a.union(&b).collect();
658 /// assert_eq!(union, [1, 2, 3, 4].iter().collect());
659 /// ```
660 #[inline]
661 #[rustc_lint_query_instability]
662 #[stable(feature = "rust1", since = "1.0.0")]
663 pub fn union<'a>(&'a self, other: &'a HashSet<T, S>) -> Union<'a, T, S> {
664 if self.len() >= other.len() {
665 Union { iter: self.iter().chain(other.difference(self)) }
666 } else {
667 Union { iter: other.iter().chain(self.difference(other)) }
668 }
669 }
670
671 /// Returns `true` if the set contains a value.
672 ///
673 /// The value may be any borrowed form of the set's value type, but
674 /// [`Hash`] and [`Eq`] on the borrowed form *must* match those for
675 /// the value type.
676 ///
677 /// # Examples
678 ///
679 /// ```
680 /// use std::collections::HashSet;
681 ///
682 /// let set = HashSet::from([1, 2, 3]);
683 /// assert_eq!(set.contains(&1), true);
684 /// assert_eq!(set.contains(&4), false);
685 /// ```
686 #[inline]
687 #[stable(feature = "rust1", since = "1.0.0")]
688 pub fn contains<Q: ?Sized>(&self, value: &Q) -> bool
689 where
690 T: Borrow<Q>,
691 Q: Hash + Eq,
692 {
693 self.base.contains(value)
694 }
695
696 /// Returns a reference to the value in the set, if any, that is equal to the given value.
697 ///
698 /// The value may be any borrowed form of the set's value type, but
699 /// [`Hash`] and [`Eq`] on the borrowed form *must* match those for
700 /// the value type.
701 ///
702 /// # Examples
703 ///
704 /// ```
705 /// use std::collections::HashSet;
706 ///
707 /// let set = HashSet::from([1, 2, 3]);
708 /// assert_eq!(set.get(&2), Some(&2));
709 /// assert_eq!(set.get(&4), None);
710 /// ```
711 #[inline]
712 #[stable(feature = "set_recovery", since = "1.9.0")]
713 pub fn get<Q: ?Sized>(&self, value: &Q) -> Option<&T>
714 where
715 T: Borrow<Q>,
716 Q: Hash + Eq,
717 {
718 self.base.get(value)
719 }
720
721 /// Inserts the given `value` into the set if it is not present, then
722 /// returns a reference to the value in the set.
723 ///
724 /// # Examples
725 ///
726 /// ```
727 /// #![feature(hash_set_entry)]
728 ///
729 /// use std::collections::HashSet;
730 ///
731 /// let mut set = HashSet::from([1, 2, 3]);
732 /// assert_eq!(set.len(), 3);
733 /// assert_eq!(set.get_or_insert(2), &2);
734 /// assert_eq!(set.get_or_insert(100), &100);
735 /// assert_eq!(set.len(), 4); // 100 was inserted
736 /// ```
737 #[inline]
738 #[unstable(feature = "hash_set_entry", issue = "60896")]
739 pub fn get_or_insert(&mut self, value: T) -> &T {
740 // Although the raw entry gives us `&mut T`, we only return `&T` to be consistent with
741 // `get`. Key mutation is "raw" because you're not supposed to affect `Eq` or `Hash`.
742 self.base.get_or_insert(value)
743 }
744
745 /// Inserts a value computed from `f` into the set if the given `value` is
746 /// not present, then returns a reference to the value in the set.
747 ///
748 /// # Examples
749 ///
750 /// ```
751 /// #![feature(hash_set_entry)]
752 ///
753 /// use std::collections::HashSet;
754 ///
755 /// let mut set: HashSet<String> = ["cat", "dog", "horse"]
756 /// .iter().map(|&pet| pet.to_owned()).collect();
757 ///
758 /// assert_eq!(set.len(), 3);
759 /// for &pet in &["cat", "dog", "fish"] {
760 /// let value = set.get_or_insert_with(pet, str::to_owned);
761 /// assert_eq!(value, pet);
762 /// }
763 /// assert_eq!(set.len(), 4); // a new "fish" was inserted
764 /// ```
765 #[inline]
766 #[unstable(feature = "hash_set_entry", issue = "60896")]
767 pub fn get_or_insert_with<Q: ?Sized, F>(&mut self, value: &Q, f: F) -> &T
768 where
769 T: Borrow<Q>,
770 Q: Hash + Eq,
771 F: FnOnce(&Q) -> T,
772 {
773 // Although the raw entry gives us `&mut T`, we only return `&T` to be consistent with
774 // `get`. Key mutation is "raw" because you're not supposed to affect `Eq` or `Hash`.
775 self.base.get_or_insert_with(value, f)
776 }
777
778 /// Gets the given value's corresponding entry in the set for in-place manipulation.
779 ///
780 /// # Examples
781 ///
782 /// ```
783 /// #![feature(hash_set_entry)]
784 ///
785 /// use std::collections::HashSet;
786 /// use std::collections::hash_set::Entry::*;
787 ///
788 /// let mut singles = HashSet::new();
789 /// let mut dupes = HashSet::new();
790 ///
791 /// for ch in "a short treatise on fungi".chars() {
792 /// if let Vacant(dupe_entry) = dupes.entry(ch) {
793 /// // We haven't already seen a duplicate, so
794 /// // check if we've at least seen it once.
795 /// match singles.entry(ch) {
796 /// Vacant(single_entry) => {
797 /// // We found a new character for the first time.
798 /// single_entry.insert()
799 /// }
800 /// Occupied(single_entry) => {
801 /// // We've already seen this once, "move" it to dupes.
802 /// single_entry.remove();
803 /// dupe_entry.insert();
804 /// }
805 /// }
806 /// }
807 /// }
808 ///
809 /// assert!(!singles.contains(&'t') && dupes.contains(&'t'));
810 /// assert!(singles.contains(&'u') && !dupes.contains(&'u'));
811 /// assert!(!singles.contains(&'v') && !dupes.contains(&'v'));
812 /// ```
813 #[inline]
814 #[unstable(feature = "hash_set_entry", issue = "60896")]
815 pub fn entry(&mut self, value: T) -> Entry<'_, T, S> {
816 map_entry(self.base.entry(value))
817 }
818
819 /// Returns `true` if `self` has no elements in common with `other`.
820 /// This is equivalent to checking for an empty intersection.
821 ///
822 /// # Examples
823 ///
824 /// ```
825 /// use std::collections::HashSet;
826 ///
827 /// let a = HashSet::from([1, 2, 3]);
828 /// let mut b = HashSet::new();
829 ///
830 /// assert_eq!(a.is_disjoint(&b), true);
831 /// b.insert(4);
832 /// assert_eq!(a.is_disjoint(&b), true);
833 /// b.insert(1);
834 /// assert_eq!(a.is_disjoint(&b), false);
835 /// ```
836 #[stable(feature = "rust1", since = "1.0.0")]
837 pub fn is_disjoint(&self, other: &HashSet<T, S>) -> bool {
838 if self.len() <= other.len() {
839 self.iter().all(|v| !other.contains(v))
840 } else {
841 other.iter().all(|v| !self.contains(v))
842 }
843 }
844
845 /// Returns `true` if the set is a subset of another,
846 /// i.e., `other` contains at least all the values in `self`.
847 ///
848 /// # Examples
849 ///
850 /// ```
851 /// use std::collections::HashSet;
852 ///
853 /// let sup = HashSet::from([1, 2, 3]);
854 /// let mut set = HashSet::new();
855 ///
856 /// assert_eq!(set.is_subset(&sup), true);
857 /// set.insert(2);
858 /// assert_eq!(set.is_subset(&sup), true);
859 /// set.insert(4);
860 /// assert_eq!(set.is_subset(&sup), false);
861 /// ```
862 #[stable(feature = "rust1", since = "1.0.0")]
863 pub fn is_subset(&self, other: &HashSet<T, S>) -> bool {
864 if self.len() <= other.len() { self.iter().all(|v| other.contains(v)) } else { false }
865 }
866
867 /// Returns `true` if the set is a superset of another,
868 /// i.e., `self` contains at least all the values in `other`.
869 ///
870 /// # Examples
871 ///
872 /// ```
873 /// use std::collections::HashSet;
874 ///
875 /// let sub = HashSet::from([1, 2]);
876 /// let mut set = HashSet::new();
877 ///
878 /// assert_eq!(set.is_superset(&sub), false);
879 ///
880 /// set.insert(0);
881 /// set.insert(1);
882 /// assert_eq!(set.is_superset(&sub), false);
883 ///
884 /// set.insert(2);
885 /// assert_eq!(set.is_superset(&sub), true);
886 /// ```
887 #[inline]
888 #[stable(feature = "rust1", since = "1.0.0")]
889 pub fn is_superset(&self, other: &HashSet<T, S>) -> bool {
890 other.is_subset(self)
891 }
892
893 /// Adds a value to the set.
894 ///
895 /// Returns whether the value was newly inserted. That is:
896 ///
897 /// - If the set did not previously contain this value, `true` is returned.
898 /// - If the set already contained this value, `false` is returned,
899 /// and the set is not modified: original value is not replaced,
900 /// and the value passed as argument is dropped.
901 ///
902 /// # Examples
903 ///
904 /// ```
905 /// use std::collections::HashSet;
906 ///
907 /// let mut set = HashSet::new();
908 ///
909 /// assert_eq!(set.insert(2), true);
910 /// assert_eq!(set.insert(2), false);
911 /// assert_eq!(set.len(), 1);
912 /// ```
913 #[inline]
914 #[stable(feature = "rust1", since = "1.0.0")]
915 #[rustc_confusables("push", "append", "put")]
916 pub fn insert(&mut self, value: T) -> bool {
917 self.base.insert(value)
918 }
919
920 /// Adds a value to the set, replacing the existing value, if any, that is equal to the given
921 /// one. Returns the replaced value.
922 ///
923 /// # Examples
924 ///
925 /// ```
926 /// use std::collections::HashSet;
927 ///
928 /// let mut set = HashSet::new();
929 /// set.insert(Vec::<i32>::new());
930 ///
931 /// assert_eq!(set.get(&[][..]).unwrap().capacity(), 0);
932 /// set.replace(Vec::with_capacity(10));
933 /// assert_eq!(set.get(&[][..]).unwrap().capacity(), 10);
934 /// ```
935 #[inline]
936 #[stable(feature = "set_recovery", since = "1.9.0")]
937 #[rustc_confusables("swap")]
938 pub fn replace(&mut self, value: T) -> Option<T> {
939 self.base.replace(value)
940 }
941
942 /// Removes a value from the set. Returns whether the value was
943 /// present in the set.
944 ///
945 /// The value may be any borrowed form of the set's value type, but
946 /// [`Hash`] and [`Eq`] on the borrowed form *must* match those for
947 /// the value type.
948 ///
949 /// # Examples
950 ///
951 /// ```
952 /// use std::collections::HashSet;
953 ///
954 /// let mut set = HashSet::new();
955 ///
956 /// set.insert(2);
957 /// assert_eq!(set.remove(&2), true);
958 /// assert_eq!(set.remove(&2), false);
959 /// ```
960 #[inline]
961 #[stable(feature = "rust1", since = "1.0.0")]
962 #[rustc_confusables("delete", "take")]
963 pub fn remove<Q: ?Sized>(&mut self, value: &Q) -> bool
964 where
965 T: Borrow<Q>,
966 Q: Hash + Eq,
967 {
968 self.base.remove(value)
969 }
970
971 /// Removes and returns the value in the set, if any, that is equal to the given one.
972 ///
973 /// The value may be any borrowed form of the set's value type, but
974 /// [`Hash`] and [`Eq`] on the borrowed form *must* match those for
975 /// the value type.
976 ///
977 /// # Examples
978 ///
979 /// ```
980 /// use std::collections::HashSet;
981 ///
982 /// let mut set = HashSet::from([1, 2, 3]);
983 /// assert_eq!(set.take(&2), Some(2));
984 /// assert_eq!(set.take(&2), None);
985 /// ```
986 #[inline]
987 #[stable(feature = "set_recovery", since = "1.9.0")]
988 pub fn take<Q: ?Sized>(&mut self, value: &Q) -> Option<T>
989 where
990 T: Borrow<Q>,
991 Q: Hash + Eq,
992 {
993 self.base.take(value)
994 }
995}
996
997#[inline]
998fn map_entry<'a, K: 'a, V: 'a>(raw: base::Entry<'a, K, V>) -> Entry<'a, K, V> {
999 match raw {
1000 base::Entry::Occupied(base) => Entry::Occupied(OccupiedEntry { base }),
1001 base::Entry::Vacant(base) => Entry::Vacant(VacantEntry { base }),
1002 }
1003}
1004
1005#[stable(feature = "rust1", since = "1.0.0")]
1006impl<T, S> Clone for HashSet<T, S>
1007where
1008 T: Clone,
1009 S: Clone,
1010{
1011 #[inline]
1012 fn clone(&self) -> Self {
1013 Self { base: self.base.clone() }
1014 }
1015
1016 /// Overwrites the contents of `self` with a clone of the contents of `source`.
1017 ///
1018 /// This method is preferred over simply assigning `source.clone()` to `self`,
1019 /// as it avoids reallocation if possible.
1020 #[inline]
1021 fn clone_from(&mut self, other: &Self) {
1022 self.base.clone_from(&other.base);
1023 }
1024}
1025
1026#[stable(feature = "rust1", since = "1.0.0")]
1027impl<T, S> PartialEq for HashSet<T, S>
1028where
1029 T: Eq + Hash,
1030 S: BuildHasher,
1031{
1032 fn eq(&self, other: &HashSet<T, S>) -> bool {
1033 if self.len() != other.len() {
1034 return false;
1035 }
1036
1037 self.iter().all(|key| other.contains(key))
1038 }
1039}
1040
1041#[stable(feature = "rust1", since = "1.0.0")]
1042impl<T, S> Eq for HashSet<T, S>
1043where
1044 T: Eq + Hash,
1045 S: BuildHasher,
1046{
1047}
1048
1049#[stable(feature = "rust1", since = "1.0.0")]
1050impl<T, S> fmt::Debug for HashSet<T, S>
1051where
1052 T: fmt::Debug,
1053{
1054 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1055 f.debug_set().entries(self.iter()).finish()
1056 }
1057}
1058
1059#[stable(feature = "rust1", since = "1.0.0")]
1060impl<T, S> FromIterator<T> for HashSet<T, S>
1061where
1062 T: Eq + Hash,
1063 S: BuildHasher + Default,
1064{
1065 #[inline]
1066 fn from_iter<I: IntoIterator<Item = T>>(iter: I) -> HashSet<T, S> {
1067 let mut set = HashSet::with_hasher(Default::default());
1068 set.extend(iter);
1069 set
1070 }
1071}
1072
1073#[stable(feature = "std_collections_from_array", since = "1.56.0")]
1074// Note: as what is currently the most convenient built-in way to construct
1075// a HashSet, a simple usage of this function must not *require* the user
1076// to provide a type annotation in order to infer the third type parameter
1077// (the hasher parameter, conventionally "S").
1078// To that end, this impl is defined using RandomState as the concrete
1079// type of S, rather than being generic over `S: BuildHasher + Default`.
1080// It is expected that users who want to specify a hasher will manually use
1081// `with_capacity_and_hasher`.
1082// If type parameter defaults worked on impls, and if type parameter
1083// defaults could be mixed with const generics, then perhaps
1084// this could be generalized.
1085// See also the equivalent impl on HashMap.
1086impl<T, const N: usize> From<[T; N]> for HashSet<T, RandomState>
1087where
1088 T: Eq + Hash,
1089{
1090 /// Converts a `[T; N]` into a `HashSet<T>`.
1091 ///
1092 /// If the array contains any equal values,
1093 /// all but one will be dropped.
1094 ///
1095 /// # Examples
1096 ///
1097 /// ```
1098 /// use std::collections::HashSet;
1099 ///
1100 /// let set1 = HashSet::from([1, 2, 3, 4]);
1101 /// let set2: HashSet<_> = [1, 2, 3, 4].into();
1102 /// assert_eq!(set1, set2);
1103 /// ```
1104 fn from(arr: [T; N]) -> Self {
1105 Self::from_iter(arr)
1106 }
1107}
1108
1109#[stable(feature = "rust1", since = "1.0.0")]
1110impl<T, S> Extend<T> for HashSet<T, S>
1111where
1112 T: Eq + Hash,
1113 S: BuildHasher,
1114{
1115 #[inline]
1116 fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {
1117 self.base.extend(iter);
1118 }
1119
1120 #[inline]
1121 fn extend_one(&mut self, item: T) {
1122 self.base.insert(item);
1123 }
1124
1125 #[inline]
1126 fn extend_reserve(&mut self, additional: usize) {
1127 self.base.extend_reserve(additional);
1128 }
1129}
1130
1131#[stable(feature = "hash_extend_copy", since = "1.4.0")]
1132impl<'a, T, S> Extend<&'a T> for HashSet<T, S>
1133where
1134 T: 'a + Eq + Hash + Copy,
1135 S: BuildHasher,
1136{
1137 #[inline]
1138 fn extend<I: IntoIterator<Item = &'a T>>(&mut self, iter: I) {
1139 self.extend(iter.into_iter().cloned());
1140 }
1141
1142 #[inline]
1143 fn extend_one(&mut self, &item: &'a T) {
1144 self.base.insert(item);
1145 }
1146
1147 #[inline]
1148 fn extend_reserve(&mut self, additional: usize) {
1149 Extend::<T>::extend_reserve(self, additional)
1150 }
1151}
1152
1153#[stable(feature = "rust1", since = "1.0.0")]
1154impl<T, S> Default for HashSet<T, S>
1155where
1156 S: Default,
1157{
1158 /// Creates an empty `HashSet<T, S>` with the `Default` value for the hasher.
1159 #[inline]
1160 fn default() -> HashSet<T, S> {
1161 HashSet { base: Default::default() }
1162 }
1163}
1164
1165#[stable(feature = "rust1", since = "1.0.0")]
1166impl<T, S> BitOr<&HashSet<T, S>> for &HashSet<T, S>
1167where
1168 T: Eq + Hash + Clone,
1169 S: BuildHasher + Default,
1170{
1171 type Output = HashSet<T, S>;
1172
1173 /// Returns the union of `self` and `rhs` as a new `HashSet<T, S>`.
1174 ///
1175 /// # Examples
1176 ///
1177 /// ```
1178 /// use std::collections::HashSet;
1179 ///
1180 /// let a = HashSet::from([1, 2, 3]);
1181 /// let b = HashSet::from([3, 4, 5]);
1182 ///
1183 /// let set = &a | &b;
1184 ///
1185 /// let mut i = 0;
1186 /// let expected = [1, 2, 3, 4, 5];
1187 /// for x in &set {
1188 /// assert!(expected.contains(x));
1189 /// i += 1;
1190 /// }
1191 /// assert_eq!(i, expected.len());
1192 /// ```
1193 fn bitor(self, rhs: &HashSet<T, S>) -> HashSet<T, S> {
1194 self.union(rhs).cloned().collect()
1195 }
1196}
1197
1198#[stable(feature = "rust1", since = "1.0.0")]
1199impl<T, S> BitAnd<&HashSet<T, S>> for &HashSet<T, S>
1200where
1201 T: Eq + Hash + Clone,
1202 S: BuildHasher + Default,
1203{
1204 type Output = HashSet<T, S>;
1205
1206 /// Returns the intersection of `self` and `rhs` as a new `HashSet<T, S>`.
1207 ///
1208 /// # Examples
1209 ///
1210 /// ```
1211 /// use std::collections::HashSet;
1212 ///
1213 /// let a = HashSet::from([1, 2, 3]);
1214 /// let b = HashSet::from([2, 3, 4]);
1215 ///
1216 /// let set = &a & &b;
1217 ///
1218 /// let mut i = 0;
1219 /// let expected = [2, 3];
1220 /// for x in &set {
1221 /// assert!(expected.contains(x));
1222 /// i += 1;
1223 /// }
1224 /// assert_eq!(i, expected.len());
1225 /// ```
1226 fn bitand(self, rhs: &HashSet<T, S>) -> HashSet<T, S> {
1227 self.intersection(rhs).cloned().collect()
1228 }
1229}
1230
1231#[stable(feature = "rust1", since = "1.0.0")]
1232impl<T, S> BitXor<&HashSet<T, S>> for &HashSet<T, S>
1233where
1234 T: Eq + Hash + Clone,
1235 S: BuildHasher + Default,
1236{
1237 type Output = HashSet<T, S>;
1238
1239 /// Returns the symmetric difference of `self` and `rhs` as a new `HashSet<T, S>`.
1240 ///
1241 /// # Examples
1242 ///
1243 /// ```
1244 /// use std::collections::HashSet;
1245 ///
1246 /// let a = HashSet::from([1, 2, 3]);
1247 /// let b = HashSet::from([3, 4, 5]);
1248 ///
1249 /// let set = &a ^ &b;
1250 ///
1251 /// let mut i = 0;
1252 /// let expected = [1, 2, 4, 5];
1253 /// for x in &set {
1254 /// assert!(expected.contains(x));
1255 /// i += 1;
1256 /// }
1257 /// assert_eq!(i, expected.len());
1258 /// ```
1259 fn bitxor(self, rhs: &HashSet<T, S>) -> HashSet<T, S> {
1260 self.symmetric_difference(rhs).cloned().collect()
1261 }
1262}
1263
1264#[stable(feature = "rust1", since = "1.0.0")]
1265impl<T, S> Sub<&HashSet<T, S>> for &HashSet<T, S>
1266where
1267 T: Eq + Hash + Clone,
1268 S: BuildHasher + Default,
1269{
1270 type Output = HashSet<T, S>;
1271
1272 /// Returns the difference of `self` and `rhs` as a new `HashSet<T, S>`.
1273 ///
1274 /// # Examples
1275 ///
1276 /// ```
1277 /// use std::collections::HashSet;
1278 ///
1279 /// let a = HashSet::from([1, 2, 3]);
1280 /// let b = HashSet::from([3, 4, 5]);
1281 ///
1282 /// let set = &a - &b;
1283 ///
1284 /// let mut i = 0;
1285 /// let expected = [1, 2];
1286 /// for x in &set {
1287 /// assert!(expected.contains(x));
1288 /// i += 1;
1289 /// }
1290 /// assert_eq!(i, expected.len());
1291 /// ```
1292 fn sub(self, rhs: &HashSet<T, S>) -> HashSet<T, S> {
1293 self.difference(rhs).cloned().collect()
1294 }
1295}
1296
1297/// An iterator over the items of a `HashSet`.
1298///
1299/// This `struct` is created by the [`iter`] method on [`HashSet`].
1300/// See its documentation for more.
1301///
1302/// [`iter`]: HashSet::iter
1303///
1304/// # Examples
1305///
1306/// ```
1307/// use std::collections::HashSet;
1308///
1309/// let a = HashSet::from([1, 2, 3]);
1310///
1311/// let mut iter = a.iter();
1312/// ```
1313#[stable(feature = "rust1", since = "1.0.0")]
1314#[cfg_attr(not(test), rustc_diagnostic_item = "hashset_iter_ty")]
1315pub struct Iter<'a, K: 'a> {
1316 base: base::Iter<'a, K>,
1317}
1318
1319#[stable(feature = "default_iters_hash", since = "1.83.0")]
1320impl<K> Default for Iter<'_, K> {
1321 #[inline]
1322 fn default() -> Self {
1323 Iter { base: Default::default() }
1324 }
1325}
1326
1327/// An owning iterator over the items of a `HashSet`.
1328///
1329/// This `struct` is created by the [`into_iter`] method on [`HashSet`]
1330/// (provided by the [`IntoIterator`] trait). See its documentation for more.
1331///
1332/// [`into_iter`]: IntoIterator::into_iter
1333///
1334/// # Examples
1335///
1336/// ```
1337/// use std::collections::HashSet;
1338///
1339/// let a = HashSet::from([1, 2, 3]);
1340///
1341/// let mut iter = a.into_iter();
1342/// ```
1343#[stable(feature = "rust1", since = "1.0.0")]
1344pub struct IntoIter<K> {
1345 base: base::IntoIter<K>,
1346}
1347
1348#[stable(feature = "default_iters_hash", since = "1.83.0")]
1349impl<K> Default for IntoIter<K> {
1350 #[inline]
1351 fn default() -> Self {
1352 IntoIter { base: Default::default() }
1353 }
1354}
1355
1356/// A draining iterator over the items of a `HashSet`.
1357///
1358/// This `struct` is created by the [`drain`] method on [`HashSet`].
1359/// See its documentation for more.
1360///
1361/// [`drain`]: HashSet::drain
1362///
1363/// # Examples
1364///
1365/// ```
1366/// use std::collections::HashSet;
1367///
1368/// let mut a = HashSet::from([1, 2, 3]);
1369///
1370/// let mut drain = a.drain();
1371/// ```
1372#[stable(feature = "rust1", since = "1.0.0")]
1373#[cfg_attr(not(test), rustc_diagnostic_item = "hashset_drain_ty")]
1374pub struct Drain<'a, K: 'a> {
1375 base: base::Drain<'a, K>,
1376}
1377
1378/// A draining, filtering iterator over the items of a `HashSet`.
1379///
1380/// This `struct` is created by the [`extract_if`] method on [`HashSet`].
1381///
1382/// [`extract_if`]: HashSet::extract_if
1383///
1384/// # Examples
1385///
1386/// ```
1387/// use std::collections::HashSet;
1388///
1389/// let mut a = HashSet::from([1, 2, 3]);
1390///
1391/// let mut extract_ifed = a.extract_if(|v| v % 2 == 0);
1392/// ```
1393#[stable(feature = "hash_extract_if", since = "CURRENT_RUSTC_VERSION")]
1394pub struct ExtractIf<'a, K, F>
1395where
1396 F: FnMut(&K) -> bool,
1397{
1398 base: base::ExtractIf<'a, K, F>,
1399}
1400
1401/// A lazy iterator producing elements in the intersection of `HashSet`s.
1402///
1403/// This `struct` is created by the [`intersection`] method on [`HashSet`].
1404/// See its documentation for more.
1405///
1406/// [`intersection`]: HashSet::intersection
1407///
1408/// # Examples
1409///
1410/// ```
1411/// use std::collections::HashSet;
1412///
1413/// let a = HashSet::from([1, 2, 3]);
1414/// let b = HashSet::from([4, 2, 3, 4]);
1415///
1416/// let mut intersection = a.intersection(&b);
1417/// ```
1418#[must_use = "this returns the intersection as an iterator, \
1419 without modifying either input set"]
1420#[stable(feature = "rust1", since = "1.0.0")]
1421pub struct Intersection<'a, T: 'a, S: 'a> {
1422 // iterator of the first set
1423 iter: Iter<'a, T>,
1424 // the second set
1425 other: &'a HashSet<T, S>,
1426}
1427
1428/// A lazy iterator producing elements in the difference of `HashSet`s.
1429///
1430/// This `struct` is created by the [`difference`] method on [`HashSet`].
1431/// See its documentation for more.
1432///
1433/// [`difference`]: HashSet::difference
1434///
1435/// # Examples
1436///
1437/// ```
1438/// use std::collections::HashSet;
1439///
1440/// let a = HashSet::from([1, 2, 3]);
1441/// let b = HashSet::from([4, 2, 3, 4]);
1442///
1443/// let mut difference = a.difference(&b);
1444/// ```
1445#[must_use = "this returns the difference as an iterator, \
1446 without modifying either input set"]
1447#[stable(feature = "rust1", since = "1.0.0")]
1448pub struct Difference<'a, T: 'a, S: 'a> {
1449 // iterator of the first set
1450 iter: Iter<'a, T>,
1451 // the second set
1452 other: &'a HashSet<T, S>,
1453}
1454
1455/// A lazy iterator producing elements in the symmetric difference of `HashSet`s.
1456///
1457/// This `struct` is created by the [`symmetric_difference`] method on
1458/// [`HashSet`]. See its documentation for more.
1459///
1460/// [`symmetric_difference`]: HashSet::symmetric_difference
1461///
1462/// # Examples
1463///
1464/// ```
1465/// use std::collections::HashSet;
1466///
1467/// let a = HashSet::from([1, 2, 3]);
1468/// let b = HashSet::from([4, 2, 3, 4]);
1469///
1470/// let mut intersection = a.symmetric_difference(&b);
1471/// ```
1472#[must_use = "this returns the difference as an iterator, \
1473 without modifying either input set"]
1474#[stable(feature = "rust1", since = "1.0.0")]
1475pub struct SymmetricDifference<'a, T: 'a, S: 'a> {
1476 iter: Chain<Difference<'a, T, S>, Difference<'a, T, S>>,
1477}
1478
1479/// A lazy iterator producing elements in the union of `HashSet`s.
1480///
1481/// This `struct` is created by the [`union`] method on [`HashSet`].
1482/// See its documentation for more.
1483///
1484/// [`union`]: HashSet::union
1485///
1486/// # Examples
1487///
1488/// ```
1489/// use std::collections::HashSet;
1490///
1491/// let a = HashSet::from([1, 2, 3]);
1492/// let b = HashSet::from([4, 2, 3, 4]);
1493///
1494/// let mut union_iter = a.union(&b);
1495/// ```
1496#[must_use = "this returns the union as an iterator, \
1497 without modifying either input set"]
1498#[stable(feature = "rust1", since = "1.0.0")]
1499pub struct Union<'a, T: 'a, S: 'a> {
1500 iter: Chain<Iter<'a, T>, Difference<'a, T, S>>,
1501}
1502
1503#[stable(feature = "rust1", since = "1.0.0")]
1504impl<'a, T, S> IntoIterator for &'a HashSet<T, S> {
1505 type Item = &'a T;
1506 type IntoIter = Iter<'a, T>;
1507
1508 #[inline]
1509 #[rustc_lint_query_instability]
1510 fn into_iter(self) -> Iter<'a, T> {
1511 self.iter()
1512 }
1513}
1514
1515#[stable(feature = "rust1", since = "1.0.0")]
1516impl<T, S> IntoIterator for HashSet<T, S> {
1517 type Item = T;
1518 type IntoIter = IntoIter<T>;
1519
1520 /// Creates a consuming iterator, that is, one that moves each value out
1521 /// of the set in arbitrary order. The set cannot be used after calling
1522 /// this.
1523 ///
1524 /// # Examples
1525 ///
1526 /// ```
1527 /// use std::collections::HashSet;
1528 /// let mut set = HashSet::new();
1529 /// set.insert("a".to_string());
1530 /// set.insert("b".to_string());
1531 ///
1532 /// // Not possible to collect to a Vec<String> with a regular `.iter()`.
1533 /// let v: Vec<String> = set.into_iter().collect();
1534 ///
1535 /// // Will print in an arbitrary order.
1536 /// for x in &v {
1537 /// println!("{x}");
1538 /// }
1539 /// ```
1540 #[inline]
1541 #[rustc_lint_query_instability]
1542 fn into_iter(self) -> IntoIter<T> {
1543 IntoIter { base: self.base.into_iter() }
1544 }
1545}
1546
1547#[stable(feature = "rust1", since = "1.0.0")]
1548impl<K> Clone for Iter<'_, K> {
1549 #[inline]
1550 fn clone(&self) -> Self {
1551 Iter { base: self.base.clone() }
1552 }
1553}
1554#[stable(feature = "rust1", since = "1.0.0")]
1555impl<'a, K> Iterator for Iter<'a, K> {
1556 type Item = &'a K;
1557
1558 #[inline]
1559 fn next(&mut self) -> Option<&'a K> {
1560 self.base.next()
1561 }
1562 #[inline]
1563 fn size_hint(&self) -> (usize, Option<usize>) {
1564 self.base.size_hint()
1565 }
1566 #[inline]
1567 fn count(self) -> usize {
1568 self.base.len()
1569 }
1570 #[inline]
1571 fn fold<B, F>(self, init: B, f: F) -> B
1572 where
1573 Self: Sized,
1574 F: FnMut(B, Self::Item) -> B,
1575 {
1576 self.base.fold(init, f)
1577 }
1578}
1579#[stable(feature = "rust1", since = "1.0.0")]
1580impl<K> ExactSizeIterator for Iter<'_, K> {
1581 #[inline]
1582 fn len(&self) -> usize {
1583 self.base.len()
1584 }
1585}
1586#[stable(feature = "fused", since = "1.26.0")]
1587impl<K> FusedIterator for Iter<'_, K> {}
1588
1589#[stable(feature = "std_debug", since = "1.16.0")]
1590impl<K: fmt::Debug> fmt::Debug for Iter<'_, K> {
1591 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1592 f.debug_list().entries(self.clone()).finish()
1593 }
1594}
1595
1596#[stable(feature = "rust1", since = "1.0.0")]
1597impl<K> Iterator for IntoIter<K> {
1598 type Item = K;
1599
1600 #[inline]
1601 fn next(&mut self) -> Option<K> {
1602 self.base.next()
1603 }
1604 #[inline]
1605 fn size_hint(&self) -> (usize, Option<usize>) {
1606 self.base.size_hint()
1607 }
1608 #[inline]
1609 fn count(self) -> usize {
1610 self.base.len()
1611 }
1612 #[inline]
1613 fn fold<B, F>(self, init: B, f: F) -> B
1614 where
1615 Self: Sized,
1616 F: FnMut(B, Self::Item) -> B,
1617 {
1618 self.base.fold(init, f)
1619 }
1620}
1621#[stable(feature = "rust1", since = "1.0.0")]
1622impl<K> ExactSizeIterator for IntoIter<K> {
1623 #[inline]
1624 fn len(&self) -> usize {
1625 self.base.len()
1626 }
1627}
1628#[stable(feature = "fused", since = "1.26.0")]
1629impl<K> FusedIterator for IntoIter<K> {}
1630
1631#[stable(feature = "std_debug", since = "1.16.0")]
1632impl<K: fmt::Debug> fmt::Debug for IntoIter<K> {
1633 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1634 fmt::Debug::fmt(&self.base, f)
1635 }
1636}
1637
1638#[stable(feature = "rust1", since = "1.0.0")]
1639impl<'a, K> Iterator for Drain<'a, K> {
1640 type Item = K;
1641
1642 #[inline]
1643 fn next(&mut self) -> Option<K> {
1644 self.base.next()
1645 }
1646 #[inline]
1647 fn size_hint(&self) -> (usize, Option<usize>) {
1648 self.base.size_hint()
1649 }
1650 #[inline]
1651 fn fold<B, F>(self, init: B, f: F) -> B
1652 where
1653 Self: Sized,
1654 F: FnMut(B, Self::Item) -> B,
1655 {
1656 self.base.fold(init, f)
1657 }
1658}
1659#[stable(feature = "rust1", since = "1.0.0")]
1660impl<K> ExactSizeIterator for Drain<'_, K> {
1661 #[inline]
1662 fn len(&self) -> usize {
1663 self.base.len()
1664 }
1665}
1666#[stable(feature = "fused", since = "1.26.0")]
1667impl<K> FusedIterator for Drain<'_, K> {}
1668
1669#[stable(feature = "std_debug", since = "1.16.0")]
1670impl<K: fmt::Debug> fmt::Debug for Drain<'_, K> {
1671 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1672 fmt::Debug::fmt(&self.base, f)
1673 }
1674}
1675
1676#[stable(feature = "hash_extract_if", since = "CURRENT_RUSTC_VERSION")]
1677impl<K, F> Iterator for ExtractIf<'_, K, F>
1678where
1679 F: FnMut(&K) -> bool,
1680{
1681 type Item = K;
1682
1683 #[inline]
1684 fn next(&mut self) -> Option<K> {
1685 self.base.next()
1686 }
1687 #[inline]
1688 fn size_hint(&self) -> (usize, Option<usize>) {
1689 self.base.size_hint()
1690 }
1691}
1692
1693#[stable(feature = "hash_extract_if", since = "CURRENT_RUSTC_VERSION")]
1694impl<K, F> FusedIterator for ExtractIf<'_, K, F> where F: FnMut(&K) -> bool {}
1695
1696#[stable(feature = "hash_extract_if", since = "CURRENT_RUSTC_VERSION")]
1697impl<'a, K, F> fmt::Debug for ExtractIf<'a, K, F>
1698where
1699 F: FnMut(&K) -> bool,
1700{
1701 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1702 f.debug_struct("ExtractIf").finish_non_exhaustive()
1703 }
1704}
1705
1706#[stable(feature = "rust1", since = "1.0.0")]
1707impl<T, S> Clone for Intersection<'_, T, S> {
1708 #[inline]
1709 fn clone(&self) -> Self {
1710 Intersection { iter: self.iter.clone(), ..*self }
1711 }
1712}
1713
1714#[stable(feature = "rust1", since = "1.0.0")]
1715impl<'a, T, S> Iterator for Intersection<'a, T, S>
1716where
1717 T: Eq + Hash,
1718 S: BuildHasher,
1719{
1720 type Item = &'a T;
1721
1722 #[inline]
1723 fn next(&mut self) -> Option<&'a T> {
1724 loop {
1725 let elt = self.iter.next()?;
1726 if self.other.contains(elt) {
1727 return Some(elt);
1728 }
1729 }
1730 }
1731
1732 #[inline]
1733 fn size_hint(&self) -> (usize, Option<usize>) {
1734 let (_, upper) = self.iter.size_hint();
1735 (0, upper)
1736 }
1737
1738 #[inline]
1739 fn fold<B, F>(self, init: B, mut f: F) -> B
1740 where
1741 Self: Sized,
1742 F: FnMut(B, Self::Item) -> B,
1743 {
1744 self.iter.fold(init, |acc, elt| if self.other.contains(elt) { f(acc, elt) } else { acc })
1745 }
1746}
1747
1748#[stable(feature = "std_debug", since = "1.16.0")]
1749impl<T, S> fmt::Debug for Intersection<'_, T, S>
1750where
1751 T: fmt::Debug + Eq + Hash,
1752 S: BuildHasher,
1753{
1754 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1755 f.debug_list().entries(self.clone()).finish()
1756 }
1757}
1758
1759#[stable(feature = "fused", since = "1.26.0")]
1760impl<T, S> FusedIterator for Intersection<'_, T, S>
1761where
1762 T: Eq + Hash,
1763 S: BuildHasher,
1764{
1765}
1766
1767#[stable(feature = "rust1", since = "1.0.0")]
1768impl<T, S> Clone for Difference<'_, T, S> {
1769 #[inline]
1770 fn clone(&self) -> Self {
1771 Difference { iter: self.iter.clone(), ..*self }
1772 }
1773}
1774
1775#[stable(feature = "rust1", since = "1.0.0")]
1776impl<'a, T, S> Iterator for Difference<'a, T, S>
1777where
1778 T: Eq + Hash,
1779 S: BuildHasher,
1780{
1781 type Item = &'a T;
1782
1783 #[inline]
1784 fn next(&mut self) -> Option<&'a T> {
1785 loop {
1786 let elt = self.iter.next()?;
1787 if !self.other.contains(elt) {
1788 return Some(elt);
1789 }
1790 }
1791 }
1792
1793 #[inline]
1794 fn size_hint(&self) -> (usize, Option<usize>) {
1795 let (_, upper) = self.iter.size_hint();
1796 (0, upper)
1797 }
1798
1799 #[inline]
1800 fn fold<B, F>(self, init: B, mut f: F) -> B
1801 where
1802 Self: Sized,
1803 F: FnMut(B, Self::Item) -> B,
1804 {
1805 self.iter.fold(init, |acc, elt| if self.other.contains(elt) { acc } else { f(acc, elt) })
1806 }
1807}
1808
1809#[stable(feature = "fused", since = "1.26.0")]
1810impl<T, S> FusedIterator for Difference<'_, T, S>
1811where
1812 T: Eq + Hash,
1813 S: BuildHasher,
1814{
1815}
1816
1817#[stable(feature = "std_debug", since = "1.16.0")]
1818impl<T, S> fmt::Debug for Difference<'_, T, S>
1819where
1820 T: fmt::Debug + Eq + Hash,
1821 S: BuildHasher,
1822{
1823 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1824 f.debug_list().entries(self.clone()).finish()
1825 }
1826}
1827
1828#[stable(feature = "rust1", since = "1.0.0")]
1829impl<T, S> Clone for SymmetricDifference<'_, T, S> {
1830 #[inline]
1831 fn clone(&self) -> Self {
1832 SymmetricDifference { iter: self.iter.clone() }
1833 }
1834}
1835
1836#[stable(feature = "rust1", since = "1.0.0")]
1837impl<'a, T, S> Iterator for SymmetricDifference<'a, T, S>
1838where
1839 T: Eq + Hash,
1840 S: BuildHasher,
1841{
1842 type Item = &'a T;
1843
1844 #[inline]
1845 fn next(&mut self) -> Option<&'a T> {
1846 self.iter.next()
1847 }
1848 #[inline]
1849 fn size_hint(&self) -> (usize, Option<usize>) {
1850 self.iter.size_hint()
1851 }
1852 #[inline]
1853 fn fold<B, F>(self, init: B, f: F) -> B
1854 where
1855 Self: Sized,
1856 F: FnMut(B, Self::Item) -> B,
1857 {
1858 self.iter.fold(init, f)
1859 }
1860}
1861
1862#[stable(feature = "fused", since = "1.26.0")]
1863impl<T, S> FusedIterator for SymmetricDifference<'_, T, S>
1864where
1865 T: Eq + Hash,
1866 S: BuildHasher,
1867{
1868}
1869
1870#[stable(feature = "std_debug", since = "1.16.0")]
1871impl<T, S> fmt::Debug for SymmetricDifference<'_, T, S>
1872where
1873 T: fmt::Debug + Eq + Hash,
1874 S: BuildHasher,
1875{
1876 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1877 f.debug_list().entries(self.clone()).finish()
1878 }
1879}
1880
1881#[stable(feature = "rust1", since = "1.0.0")]
1882impl<T, S> Clone for Union<'_, T, S> {
1883 #[inline]
1884 fn clone(&self) -> Self {
1885 Union { iter: self.iter.clone() }
1886 }
1887}
1888
1889#[stable(feature = "fused", since = "1.26.0")]
1890impl<T, S> FusedIterator for Union<'_, T, S>
1891where
1892 T: Eq + Hash,
1893 S: BuildHasher,
1894{
1895}
1896
1897#[stable(feature = "std_debug", since = "1.16.0")]
1898impl<T, S> fmt::Debug for Union<'_, T, S>
1899where
1900 T: fmt::Debug + Eq + Hash,
1901 S: BuildHasher,
1902{
1903 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1904 f.debug_list().entries(self.clone()).finish()
1905 }
1906}
1907
1908#[stable(feature = "rust1", since = "1.0.0")]
1909impl<'a, T, S> Iterator for Union<'a, T, S>
1910where
1911 T: Eq + Hash,
1912 S: BuildHasher,
1913{
1914 type Item = &'a T;
1915
1916 #[inline]
1917 fn next(&mut self) -> Option<&'a T> {
1918 self.iter.next()
1919 }
1920 #[inline]
1921 fn size_hint(&self) -> (usize, Option<usize>) {
1922 self.iter.size_hint()
1923 }
1924 #[inline]
1925 fn count(self) -> usize {
1926 self.iter.count()
1927 }
1928 #[inline]
1929 fn fold<B, F>(self, init: B, f: F) -> B
1930 where
1931 Self: Sized,
1932 F: FnMut(B, Self::Item) -> B,
1933 {
1934 self.iter.fold(init, f)
1935 }
1936}
1937
1938/// A view into a single entry in a set, which may either be vacant or occupied.
1939///
1940/// This `enum` is constructed from the [`entry`] method on [`HashSet`].
1941///
1942/// [`HashSet`]: struct.HashSet.html
1943/// [`entry`]: struct.HashSet.html#method.entry
1944///
1945/// # Examples
1946///
1947/// ```
1948/// #![feature(hash_set_entry)]
1949///
1950/// use std::collections::hash_set::HashSet;
1951///
1952/// let mut set = HashSet::new();
1953/// set.extend(["a", "b", "c"]);
1954/// assert_eq!(set.len(), 3);
1955///
1956/// // Existing value (insert)
1957/// let entry = set.entry("a");
1958/// let _raw_o = entry.insert();
1959/// assert_eq!(set.len(), 3);
1960/// // Nonexistent value (insert)
1961/// set.entry("d").insert();
1962///
1963/// // Existing value (or_insert)
1964/// set.entry("b").or_insert();
1965/// // Nonexistent value (or_insert)
1966/// set.entry("e").or_insert();
1967///
1968/// println!("Our HashSet: {:?}", set);
1969///
1970/// let mut vec: Vec<_> = set.iter().copied().collect();
1971/// // The `Iter` iterator produces items in arbitrary order, so the
1972/// // items must be sorted to test them against a sorted array.
1973/// vec.sort_unstable();
1974/// assert_eq!(vec, ["a", "b", "c", "d", "e"]);
1975/// ```
1976#[unstable(feature = "hash_set_entry", issue = "60896")]
1977pub enum Entry<'a, T, S> {
1978 /// An occupied entry.
1979 ///
1980 /// # Examples
1981 ///
1982 /// ```
1983 /// #![feature(hash_set_entry)]
1984 ///
1985 /// use std::collections::hash_set::{Entry, HashSet};
1986 ///
1987 /// let mut set = HashSet::from(["a", "b"]);
1988 ///
1989 /// match set.entry("a") {
1990 /// Entry::Vacant(_) => unreachable!(),
1991 /// Entry::Occupied(_) => { }
1992 /// }
1993 /// ```
1994 Occupied(OccupiedEntry<'a, T, S>),
1995
1996 /// A vacant entry.
1997 ///
1998 /// # Examples
1999 ///
2000 /// ```
2001 /// #![feature(hash_set_entry)]
2002 ///
2003 /// use std::collections::hash_set::{Entry, HashSet};
2004 ///
2005 /// let mut set = HashSet::new();
2006 ///
2007 /// match set.entry("a") {
2008 /// Entry::Occupied(_) => unreachable!(),
2009 /// Entry::Vacant(_) => { }
2010 /// }
2011 /// ```
2012 Vacant(VacantEntry<'a, T, S>),
2013}
2014
2015#[unstable(feature = "hash_set_entry", issue = "60896")]
2016impl<T: fmt::Debug, S> fmt::Debug for Entry<'_, T, S> {
2017 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2018 match *self {
2019 Entry::Vacant(ref v) => f.debug_tuple("Entry").field(v).finish(),
2020 Entry::Occupied(ref o) => f.debug_tuple("Entry").field(o).finish(),
2021 }
2022 }
2023}
2024
2025/// A view into an occupied entry in a `HashSet`.
2026/// It is part of the [`Entry`] enum.
2027///
2028/// [`Entry`]: enum.Entry.html
2029///
2030/// # Examples
2031///
2032/// ```
2033/// #![feature(hash_set_entry)]
2034///
2035/// use std::collections::hash_set::{Entry, HashSet};
2036///
2037/// let mut set = HashSet::new();
2038/// set.extend(["a", "b", "c"]);
2039///
2040/// let _entry_o = set.entry("a").insert();
2041/// assert_eq!(set.len(), 3);
2042///
2043/// // Existing key
2044/// match set.entry("a") {
2045/// Entry::Vacant(_) => unreachable!(),
2046/// Entry::Occupied(view) => {
2047/// assert_eq!(view.get(), &"a");
2048/// }
2049/// }
2050///
2051/// assert_eq!(set.len(), 3);
2052///
2053/// // Existing key (take)
2054/// match set.entry("c") {
2055/// Entry::Vacant(_) => unreachable!(),
2056/// Entry::Occupied(view) => {
2057/// assert_eq!(view.remove(), "c");
2058/// }
2059/// }
2060/// assert_eq!(set.get(&"c"), None);
2061/// assert_eq!(set.len(), 2);
2062/// ```
2063#[unstable(feature = "hash_set_entry", issue = "60896")]
2064pub struct OccupiedEntry<'a, T, S> {
2065 base: base::OccupiedEntry<'a, T, S>,
2066}
2067
2068#[unstable(feature = "hash_set_entry", issue = "60896")]
2069impl<T: fmt::Debug, S> fmt::Debug for OccupiedEntry<'_, T, S> {
2070 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2071 f.debug_struct("OccupiedEntry").field("value", self.get()).finish()
2072 }
2073}
2074
2075/// A view into a vacant entry in a `HashSet`.
2076/// It is part of the [`Entry`] enum.
2077///
2078/// [`Entry`]: enum.Entry.html
2079///
2080/// # Examples
2081///
2082/// ```
2083/// #![feature(hash_set_entry)]
2084///
2085/// use std::collections::hash_set::{Entry, HashSet};
2086///
2087/// let mut set = HashSet::<&str>::new();
2088///
2089/// let entry_v = match set.entry("a") {
2090/// Entry::Vacant(view) => view,
2091/// Entry::Occupied(_) => unreachable!(),
2092/// };
2093/// entry_v.insert();
2094/// assert!(set.contains("a") && set.len() == 1);
2095///
2096/// // Nonexistent key (insert)
2097/// match set.entry("b") {
2098/// Entry::Vacant(view) => view.insert(),
2099/// Entry::Occupied(_) => unreachable!(),
2100/// }
2101/// assert!(set.contains("b") && set.len() == 2);
2102/// ```
2103#[unstable(feature = "hash_set_entry", issue = "60896")]
2104pub struct VacantEntry<'a, T, S> {
2105 base: base::VacantEntry<'a, T, S>,
2106}
2107
2108#[unstable(feature = "hash_set_entry", issue = "60896")]
2109impl<T: fmt::Debug, S> fmt::Debug for VacantEntry<'_, T, S> {
2110 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2111 f.debug_tuple("VacantEntry").field(self.get()).finish()
2112 }
2113}
2114
2115impl<'a, T, S> Entry<'a, T, S> {
2116 /// Sets the value of the entry, and returns an OccupiedEntry.
2117 ///
2118 /// # Examples
2119 ///
2120 /// ```
2121 /// #![feature(hash_set_entry)]
2122 ///
2123 /// use std::collections::HashSet;
2124 ///
2125 /// let mut set = HashSet::new();
2126 /// let entry = set.entry("horseyland").insert();
2127 ///
2128 /// assert_eq!(entry.get(), &"horseyland");
2129 /// ```
2130 #[inline]
2131 #[unstable(feature = "hash_set_entry", issue = "60896")]
2132 pub fn insert(self) -> OccupiedEntry<'a, T, S>
2133 where
2134 T: Hash,
2135 S: BuildHasher,
2136 {
2137 match self {
2138 Entry::Occupied(entry) => entry,
2139 Entry::Vacant(entry) => entry.insert_entry(),
2140 }
2141 }
2142
2143 /// Ensures a value is in the entry by inserting if it was vacant.
2144 ///
2145 /// # Examples
2146 ///
2147 /// ```
2148 /// #![feature(hash_set_entry)]
2149 ///
2150 /// use std::collections::HashSet;
2151 ///
2152 /// let mut set = HashSet::new();
2153 ///
2154 /// // nonexistent key
2155 /// set.entry("poneyland").or_insert();
2156 /// assert!(set.contains("poneyland"));
2157 ///
2158 /// // existing key
2159 /// set.entry("poneyland").or_insert();
2160 /// assert!(set.contains("poneyland"));
2161 /// assert_eq!(set.len(), 1);
2162 /// ```
2163 #[inline]
2164 #[unstable(feature = "hash_set_entry", issue = "60896")]
2165 pub fn or_insert(self)
2166 where
2167 T: Hash,
2168 S: BuildHasher,
2169 {
2170 if let Entry::Vacant(entry) = self {
2171 entry.insert();
2172 }
2173 }
2174
2175 /// Returns a reference to this entry's value.
2176 ///
2177 /// # Examples
2178 ///
2179 /// ```
2180 /// #![feature(hash_set_entry)]
2181 ///
2182 /// use std::collections::HashSet;
2183 ///
2184 /// let mut set = HashSet::new();
2185 /// set.entry("poneyland").or_insert();
2186 ///
2187 /// // existing key
2188 /// assert_eq!(set.entry("poneyland").get(), &"poneyland");
2189 /// // nonexistent key
2190 /// assert_eq!(set.entry("horseland").get(), &"horseland");
2191 /// ```
2192 #[inline]
2193 #[unstable(feature = "hash_set_entry", issue = "60896")]
2194 pub fn get(&self) -> &T {
2195 match *self {
2196 Entry::Occupied(ref entry) => entry.get(),
2197 Entry::Vacant(ref entry) => entry.get(),
2198 }
2199 }
2200}
2201
2202impl<T, S> OccupiedEntry<'_, T, S> {
2203 /// Gets a reference to the value in the entry.
2204 ///
2205 /// # Examples
2206 ///
2207 /// ```
2208 /// #![feature(hash_set_entry)]
2209 ///
2210 /// use std::collections::hash_set::{Entry, HashSet};
2211 ///
2212 /// let mut set = HashSet::new();
2213 /// set.entry("poneyland").or_insert();
2214 ///
2215 /// match set.entry("poneyland") {
2216 /// Entry::Vacant(_) => panic!(),
2217 /// Entry::Occupied(entry) => assert_eq!(entry.get(), &"poneyland"),
2218 /// }
2219 /// ```
2220 #[inline]
2221 #[unstable(feature = "hash_set_entry", issue = "60896")]
2222 pub fn get(&self) -> &T {
2223 self.base.get()
2224 }
2225
2226 /// Takes the value out of the entry, and returns it.
2227 /// Keeps the allocated memory for reuse.
2228 ///
2229 /// # Examples
2230 ///
2231 /// ```
2232 /// #![feature(hash_set_entry)]
2233 ///
2234 /// use std::collections::HashSet;
2235 /// use std::collections::hash_set::Entry;
2236 ///
2237 /// let mut set = HashSet::new();
2238 /// // The set is empty
2239 /// assert!(set.is_empty() && set.capacity() == 0);
2240 ///
2241 /// set.entry("poneyland").or_insert();
2242 /// let capacity_before_remove = set.capacity();
2243 ///
2244 /// if let Entry::Occupied(o) = set.entry("poneyland") {
2245 /// assert_eq!(o.remove(), "poneyland");
2246 /// }
2247 ///
2248 /// assert_eq!(set.contains("poneyland"), false);
2249 /// // Now set hold none elements but capacity is equal to the old one
2250 /// assert!(set.len() == 0 && set.capacity() == capacity_before_remove);
2251 /// ```
2252 #[inline]
2253 #[unstable(feature = "hash_set_entry", issue = "60896")]
2254 pub fn remove(self) -> T {
2255 self.base.remove()
2256 }
2257}
2258
2259impl<'a, T, S> VacantEntry<'a, T, S> {
2260 /// Gets a reference to the value that would be used when inserting
2261 /// through the `VacantEntry`.
2262 ///
2263 /// # Examples
2264 ///
2265 /// ```
2266 /// #![feature(hash_set_entry)]
2267 ///
2268 /// use std::collections::HashSet;
2269 ///
2270 /// let mut set = HashSet::new();
2271 /// assert_eq!(set.entry("poneyland").get(), &"poneyland");
2272 /// ```
2273 #[inline]
2274 #[unstable(feature = "hash_set_entry", issue = "60896")]
2275 pub fn get(&self) -> &T {
2276 self.base.get()
2277 }
2278
2279 /// Take ownership of the value.
2280 ///
2281 /// # Examples
2282 ///
2283 /// ```
2284 /// #![feature(hash_set_entry)]
2285 ///
2286 /// use std::collections::hash_set::{Entry, HashSet};
2287 ///
2288 /// let mut set = HashSet::new();
2289 ///
2290 /// match set.entry("poneyland") {
2291 /// Entry::Occupied(_) => panic!(),
2292 /// Entry::Vacant(v) => assert_eq!(v.into_value(), "poneyland"),
2293 /// }
2294 /// ```
2295 #[inline]
2296 #[unstable(feature = "hash_set_entry", issue = "60896")]
2297 pub fn into_value(self) -> T {
2298 self.base.into_value()
2299 }
2300
2301 /// Sets the value of the entry with the VacantEntry's value.
2302 ///
2303 /// # Examples
2304 ///
2305 /// ```
2306 /// #![feature(hash_set_entry)]
2307 ///
2308 /// use std::collections::HashSet;
2309 /// use std::collections::hash_set::Entry;
2310 ///
2311 /// let mut set = HashSet::new();
2312 ///
2313 /// if let Entry::Vacant(o) = set.entry("poneyland") {
2314 /// o.insert();
2315 /// }
2316 /// assert!(set.contains("poneyland"));
2317 /// ```
2318 #[inline]
2319 #[unstable(feature = "hash_set_entry", issue = "60896")]
2320 pub fn insert(self)
2321 where
2322 T: Hash,
2323 S: BuildHasher,
2324 {
2325 self.base.insert();
2326 }
2327
2328 #[inline]
2329 fn insert_entry(self) -> OccupiedEntry<'a, T, S>
2330 where
2331 T: Hash,
2332 S: BuildHasher,
2333 {
2334 OccupiedEntry { base: self.base.insert() }
2335 }
2336}
2337
2338#[allow(dead_code)]
2339fn assert_covariance() {
2340 fn set<'new>(v: HashSet<&'static str>) -> HashSet<&'new str> {
2341 v
2342 }
2343 fn iter<'a, 'new>(v: Iter<'a, &'static str>) -> Iter<'a, &'new str> {
2344 v
2345 }
2346 fn into_iter<'new>(v: IntoIter<&'static str>) -> IntoIter<&'new str> {
2347 v
2348 }
2349 fn difference<'a, 'new>(
2350 v: Difference<'a, &'static str, RandomState>,
2351 ) -> Difference<'a, &'new str, RandomState> {
2352 v
2353 }
2354 fn symmetric_difference<'a, 'new>(
2355 v: SymmetricDifference<'a, &'static str, RandomState>,
2356 ) -> SymmetricDifference<'a, &'new str, RandomState> {
2357 v
2358 }
2359 fn intersection<'a, 'new>(
2360 v: Intersection<'a, &'static str, RandomState>,
2361 ) -> Intersection<'a, &'new str, RandomState> {
2362 v
2363 }
2364 fn union<'a, 'new>(
2365 v: Union<'a, &'static str, RandomState>,
2366 ) -> Union<'a, &'new str, RandomState> {
2367 v
2368 }
2369 fn drain<'new>(d: Drain<'static, &'static str>) -> Drain<'new, &'new str> {
2370 d
2371 }
2372}