001/*
002 * Copyright (C) 2008 The Guava Authors
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016
017package com.google.common.collect;
018
019import static com.google.common.base.Preconditions.checkArgument;
020import static com.google.common.base.Preconditions.checkNotNull;
021import static com.google.common.collect.ObjectArrays.checkElementsNotNull;
022
023import com.google.common.annotations.GwtCompatible;
024import com.google.common.annotations.GwtIncompatible;
025import com.google.errorprone.annotations.CanIgnoreReturnValue;
026import com.google.errorprone.annotations.DoNotCall;
027import com.google.errorprone.annotations.concurrent.LazyInit;
028import java.io.InvalidObjectException;
029import java.io.ObjectInputStream;
030import java.io.Serializable;
031import java.util.Arrays;
032import java.util.Collection;
033import java.util.Collections;
034import java.util.Comparator;
035import java.util.Iterator;
036import java.util.NavigableSet;
037import java.util.SortedSet;
038import org.checkerframework.checker.nullness.compatqual.NullableDecl;
039
040/**
041 * A {@link NavigableSet} whose contents will never change, with many other important properties
042 * detailed at {@link ImmutableCollection}.
043 *
044 * <p><b>Warning:</b> as with any sorted collection, you are strongly advised not to use a {@link
045 * Comparator} or {@link Comparable} type whose comparison behavior is <i>inconsistent with
046 * equals</i>. That is, {@code a.compareTo(b)} or {@code comparator.compare(a, b)} should equal zero
047 * <i>if and only if</i> {@code a.equals(b)}. If this advice is not followed, the resulting
048 * collection will not correctly obey its specification.
049 *
050 * <p>See the Guava User Guide article on <a href=
051 * "https://github.com/google/guava/wiki/ImmutableCollectionsExplained"> immutable collections</a>.
052 *
053 * @author Jared Levy
054 * @author Louis Wasserman
055 * @since 2.0 (implements {@code NavigableSet} since 12.0)
056 */
057// TODO(benyu): benchmark and optimize all creation paths, which are a mess now
058@GwtCompatible(serializable = true, emulated = true)
059@SuppressWarnings("serial") // we're overriding default serialization
060public abstract class ImmutableSortedSet<E> extends ImmutableSortedSetFauxverideShim<E>
061    implements NavigableSet<E>, SortedIterable<E> {
062  static <E> RegularImmutableSortedSet<E> emptySet(Comparator<? super E> comparator) {
063    if (Ordering.natural().equals(comparator)) {
064      return (RegularImmutableSortedSet<E>) RegularImmutableSortedSet.NATURAL_EMPTY_SET;
065    } else {
066      return new RegularImmutableSortedSet<E>(ImmutableList.<E>of(), comparator);
067    }
068  }
069
070  /** Returns the empty immutable sorted set. */
071  public static <E> ImmutableSortedSet<E> of() {
072    return (ImmutableSortedSet<E>) RegularImmutableSortedSet.NATURAL_EMPTY_SET;
073  }
074
075  /** Returns an immutable sorted set containing a single element. */
076  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(E element) {
077    return new RegularImmutableSortedSet<E>(ImmutableList.of(element), Ordering.natural());
078  }
079
080  /**
081   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
082   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
083   * one specified is included.
084   *
085   * @throws NullPointerException if any element is null
086   */
087  @SuppressWarnings("unchecked")
088  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(E e1, E e2) {
089    return construct(Ordering.natural(), 2, e1, e2);
090  }
091
092  /**
093   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
094   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
095   * one specified is included.
096   *
097   * @throws NullPointerException if any element is null
098   */
099  @SuppressWarnings("unchecked")
100  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(E e1, E e2, E e3) {
101    return construct(Ordering.natural(), 3, e1, e2, e3);
102  }
103
104  /**
105   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
106   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
107   * one specified is included.
108   *
109   * @throws NullPointerException if any element is null
110   */
111  @SuppressWarnings("unchecked")
112  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(E e1, E e2, E e3, E e4) {
113    return construct(Ordering.natural(), 4, e1, e2, e3, e4);
114  }
115
116  /**
117   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
118   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
119   * one specified is included.
120   *
121   * @throws NullPointerException if any element is null
122   */
123  @SuppressWarnings("unchecked")
124  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
125      E e1, E e2, E e3, E e4, E e5) {
126    return construct(Ordering.natural(), 5, e1, e2, e3, e4, e5);
127  }
128
129  /**
130   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
131   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
132   * one specified is included.
133   *
134   * @throws NullPointerException if any element is null
135   * @since 3.0 (source-compatible since 2.0)
136   */
137  @SuppressWarnings("unchecked")
138  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
139      E e1, E e2, E e3, E e4, E e5, E e6, E... remaining) {
140    Comparable[] contents = new Comparable[6 + remaining.length];
141    contents[0] = e1;
142    contents[1] = e2;
143    contents[2] = e3;
144    contents[3] = e4;
145    contents[4] = e5;
146    contents[5] = e6;
147    System.arraycopy(remaining, 0, contents, 6, remaining.length);
148    return construct(Ordering.natural(), contents.length, (E[]) contents);
149  }
150
151  // TODO(kevinb): Consider factory methods that reject duplicates
152
153  /**
154   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
155   * When multiple elements are equivalent according to {@link Comparable#compareTo}, only the first
156   * one specified is included.
157   *
158   * @throws NullPointerException if any of {@code elements} is null
159   * @since 3.0
160   */
161  public static <E extends Comparable<? super E>> ImmutableSortedSet<E> copyOf(E[] elements) {
162    return construct(Ordering.natural(), elements.length, elements.clone());
163  }
164
165  /**
166   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
167   * When multiple elements are equivalent according to {@code compareTo()}, only the first one
168   * specified is included. To create a copy of a {@code SortedSet} that preserves the comparator,
169   * call {@link #copyOfSorted} instead. This method iterates over {@code elements} at most once.
170   *
171   * <p>Note that if {@code s} is a {@code Set<String>}, then {@code ImmutableSortedSet.copyOf(s)}
172   * returns an {@code ImmutableSortedSet<String>} containing each of the strings in {@code s},
173   * while {@code ImmutableSortedSet.of(s)} returns an {@code ImmutableSortedSet<Set<String>>}
174   * containing one element (the given set itself).
175   *
176   * <p>Despite the method name, this method attempts to avoid actually copying the data when it is
177   * safe to do so. The exact circumstances under which a copy will or will not be performed are
178   * undocumented and subject to change.
179   *
180   * <p>This method is not type-safe, as it may be called on elements that are not mutually
181   * comparable.
182   *
183   * @throws ClassCastException if the elements are not mutually comparable
184   * @throws NullPointerException if any of {@code elements} is null
185   */
186  public static <E> ImmutableSortedSet<E> copyOf(Iterable<? extends E> elements) {
187    // Hack around E not being a subtype of Comparable.
188    // Unsafe, see ImmutableSortedSetFauxverideShim.
189    @SuppressWarnings("unchecked")
190    Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
191    return copyOf(naturalOrder, elements);
192  }
193
194  /**
195   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
196   * When multiple elements are equivalent according to {@code compareTo()}, only the first one
197   * specified is included. To create a copy of a {@code SortedSet} that preserves the comparator,
198   * call {@link #copyOfSorted} instead. This method iterates over {@code elements} at most once.
199   *
200   * <p>Note that if {@code s} is a {@code Set<String>}, then {@code ImmutableSortedSet.copyOf(s)}
201   * returns an {@code ImmutableSortedSet<String>} containing each of the strings in {@code s},
202   * while {@code ImmutableSortedSet.of(s)} returns an {@code ImmutableSortedSet<Set<String>>}
203   * containing one element (the given set itself).
204   *
205   * <p><b>Note:</b> Despite what the method name suggests, if {@code elements} is an {@code
206   * ImmutableSortedSet}, it may be returned instead of a copy.
207   *
208   * <p>This method is not type-safe, as it may be called on elements that are not mutually
209   * comparable.
210   *
211   * <p>This method is safe to use even when {@code elements} is a synchronized or concurrent
212   * collection that is currently being modified by another thread.
213   *
214   * @throws ClassCastException if the elements are not mutually comparable
215   * @throws NullPointerException if any of {@code elements} is null
216   * @since 7.0 (source-compatible since 2.0)
217   */
218  public static <E> ImmutableSortedSet<E> copyOf(Collection<? extends E> elements) {
219    // Hack around E not being a subtype of Comparable.
220    // Unsafe, see ImmutableSortedSetFauxverideShim.
221    @SuppressWarnings("unchecked")
222    Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
223    return copyOf(naturalOrder, elements);
224  }
225
226  /**
227   * Returns an immutable sorted set containing the given elements sorted by their natural ordering.
228   * When multiple elements are equivalent according to {@code compareTo()}, only the first one
229   * specified is included.
230   *
231   * <p>This method is not type-safe, as it may be called on elements that are not mutually
232   * comparable.
233   *
234   * @throws ClassCastException if the elements are not mutually comparable
235   * @throws NullPointerException if any of {@code elements} is null
236   */
237  public static <E> ImmutableSortedSet<E> copyOf(Iterator<? extends E> elements) {
238    // Hack around E not being a subtype of Comparable.
239    // Unsafe, see ImmutableSortedSetFauxverideShim.
240    @SuppressWarnings("unchecked")
241    Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
242    return copyOf(naturalOrder, elements);
243  }
244
245  /**
246   * Returns an immutable sorted set containing the given elements sorted by the given {@code
247   * Comparator}. When multiple elements are equivalent according to {@code compareTo()}, only the
248   * first one specified is included.
249   *
250   * @throws NullPointerException if {@code comparator} or any of {@code elements} is null
251   */
252  public static <E> ImmutableSortedSet<E> copyOf(
253      Comparator<? super E> comparator, Iterator<? extends E> elements) {
254    return new Builder<E>(comparator).addAll(elements).build();
255  }
256
257  /**
258   * Returns an immutable sorted set containing the given elements sorted by the given {@code
259   * Comparator}. When multiple elements are equivalent according to {@code compare()}, only the
260   * first one specified is included. This method iterates over {@code elements} at most once.
261   *
262   * <p>Despite the method name, this method attempts to avoid actually copying the data when it is
263   * safe to do so. The exact circumstances under which a copy will or will not be performed are
264   * undocumented and subject to change.
265   *
266   * @throws NullPointerException if {@code comparator} or any of {@code elements} is null
267   */
268  public static <E> ImmutableSortedSet<E> copyOf(
269      Comparator<? super E> comparator, Iterable<? extends E> elements) {
270    checkNotNull(comparator);
271    boolean hasSameComparator = SortedIterables.hasSameComparator(comparator, elements);
272
273    if (hasSameComparator && (elements instanceof ImmutableSortedSet)) {
274      @SuppressWarnings("unchecked")
275      ImmutableSortedSet<E> original = (ImmutableSortedSet<E>) elements;
276      if (!original.isPartialView()) {
277        return original;
278      }
279    }
280    @SuppressWarnings("unchecked") // elements only contains E's; it's safe.
281    E[] array = (E[]) Iterables.toArray(elements);
282    return construct(comparator, array.length, array);
283  }
284
285  /**
286   * Returns an immutable sorted set containing the given elements sorted by the given {@code
287   * Comparator}. When multiple elements are equivalent according to {@code compareTo()}, only the
288   * first one specified is included.
289   *
290   * <p>Despite the method name, this method attempts to avoid actually copying the data when it is
291   * safe to do so. The exact circumstances under which a copy will or will not be performed are
292   * undocumented and subject to change.
293   *
294   * <p>This method is safe to use even when {@code elements} is a synchronized or concurrent
295   * collection that is currently being modified by another thread.
296   *
297   * @throws NullPointerException if {@code comparator} or any of {@code elements} is null
298   * @since 7.0 (source-compatible since 2.0)
299   */
300  public static <E> ImmutableSortedSet<E> copyOf(
301      Comparator<? super E> comparator, Collection<? extends E> elements) {
302    return copyOf(comparator, (Iterable<? extends E>) elements);
303  }
304
305  /**
306   * Returns an immutable sorted set containing the elements of a sorted set, sorted by the same
307   * {@code Comparator}. That behavior differs from {@link #copyOf(Iterable)}, which always uses the
308   * natural ordering of the elements.
309   *
310   * <p>Despite the method name, this method attempts to avoid actually copying the data when it is
311   * safe to do so. The exact circumstances under which a copy will or will not be performed are
312   * undocumented and subject to change.
313   *
314   * <p>This method is safe to use even when {@code sortedSet} is a synchronized or concurrent
315   * collection that is currently being modified by another thread.
316   *
317   * @throws NullPointerException if {@code sortedSet} or any of its elements is null
318   */
319  public static <E> ImmutableSortedSet<E> copyOfSorted(SortedSet<E> sortedSet) {
320    Comparator<? super E> comparator = SortedIterables.comparator(sortedSet);
321    ImmutableList<E> list = ImmutableList.copyOf(sortedSet);
322    if (list.isEmpty()) {
323      return emptySet(comparator);
324    } else {
325      return new RegularImmutableSortedSet<E>(list, comparator);
326    }
327  }
328
329  /**
330   * Constructs an {@code ImmutableSortedSet} from the first {@code n} elements of {@code contents}.
331   * If {@code k} is the size of the returned {@code ImmutableSortedSet}, then the sorted unique
332   * elements are in the first {@code k} positions of {@code contents}, and {@code contents[i] ==
333   * null} for {@code k <= i < n}.
334   *
335   * <p>This method takes ownership of {@code contents}; do not modify {@code contents} after this
336   * returns.
337   *
338   * @throws NullPointerException if any of the first {@code n} elements of {@code contents} is null
339   */
340  static <E> ImmutableSortedSet<E> construct(
341      Comparator<? super E> comparator, int n, E... contents) {
342    if (n == 0) {
343      return emptySet(comparator);
344    }
345    checkElementsNotNull(contents, n);
346    Arrays.sort(contents, 0, n, comparator);
347    int uniques = 1;
348    for (int i = 1; i < n; i++) {
349      E cur = contents[i];
350      E prev = contents[uniques - 1];
351      if (comparator.compare(cur, prev) != 0) {
352        contents[uniques++] = cur;
353      }
354    }
355    Arrays.fill(contents, uniques, n, null);
356    if (uniques < contents.length / 2) {
357      // Deduplication eliminated many of the elements.  We don't want to retain an arbitrarily
358      // large array relative to the number of elements, so we cap the ratio.
359      contents = Arrays.copyOf(contents, uniques);
360    }
361    return new RegularImmutableSortedSet<E>(
362        ImmutableList.<E>asImmutableList(contents, uniques), comparator);
363  }
364
365  /**
366   * Returns a builder that creates immutable sorted sets with an explicit comparator. If the
367   * comparator has a more general type than the set being generated, such as creating a {@code
368   * SortedSet<Integer>} with a {@code Comparator<Number>}, use the {@link Builder} constructor
369   * instead.
370   *
371   * @throws NullPointerException if {@code comparator} is null
372   */
373  public static <E> Builder<E> orderedBy(Comparator<E> comparator) {
374    return new Builder<E>(comparator);
375  }
376
377  /**
378   * Returns a builder that creates immutable sorted sets whose elements are ordered by the reverse
379   * of their natural ordering.
380   */
381  public static <E extends Comparable<?>> Builder<E> reverseOrder() {
382    return new Builder<E>(Collections.reverseOrder());
383  }
384
385  /**
386   * Returns a builder that creates immutable sorted sets whose elements are ordered by their
387   * natural ordering. The sorted sets use {@link Ordering#natural()} as the comparator. This method
388   * provides more type-safety than {@link #builder}, as it can be called only for classes that
389   * implement {@link Comparable}.
390   */
391  public static <E extends Comparable<?>> Builder<E> naturalOrder() {
392    return new Builder<E>(Ordering.natural());
393  }
394
395  /**
396   * A builder for creating immutable sorted set instances, especially {@code public static final}
397   * sets ("constant sets"), with a given comparator. Example:
398   *
399   * <pre>{@code
400   * public static final ImmutableSortedSet<Number> LUCKY_NUMBERS =
401   *     new ImmutableSortedSet.Builder<Number>(ODDS_FIRST_COMPARATOR)
402   *         .addAll(SINGLE_DIGIT_PRIMES)
403   *         .add(42)
404   *         .build();
405   * }</pre>
406   *
407   * <p>Builder instances can be reused; it is safe to call {@link #build} multiple times to build
408   * multiple sets in series. Each set is a superset of the set created before it.
409   *
410   * @since 2.0
411   */
412  public static final class Builder<E> extends ImmutableSet.Builder<E> {
413    private final Comparator<? super E> comparator;
414
415    /**
416     * Creates a new builder. The returned builder is equivalent to the builder generated by {@link
417     * ImmutableSortedSet#orderedBy}.
418     */
419    public Builder(Comparator<? super E> comparator) {
420      this.comparator = checkNotNull(comparator);
421    }
422
423    /**
424     * Adds {@code element} to the {@code ImmutableSortedSet}. If the {@code ImmutableSortedSet}
425     * already contains {@code element}, then {@code add} has no effect. (only the previously added
426     * element is retained).
427     *
428     * @param element the element to add
429     * @return this {@code Builder} object
430     * @throws NullPointerException if {@code element} is null
431     */
432    @CanIgnoreReturnValue
433    @Override
434    public Builder<E> add(E element) {
435      super.add(element);
436      return this;
437    }
438
439    /**
440     * Adds each element of {@code elements} to the {@code ImmutableSortedSet}, ignoring duplicate
441     * elements (only the first duplicate element is added).
442     *
443     * @param elements the elements to add
444     * @return this {@code Builder} object
445     * @throws NullPointerException if {@code elements} contains a null element
446     */
447    @CanIgnoreReturnValue
448    @Override
449    public Builder<E> add(E... elements) {
450      super.add(elements);
451      return this;
452    }
453
454    /**
455     * Adds each element of {@code elements} to the {@code ImmutableSortedSet}, ignoring duplicate
456     * elements (only the first duplicate element is added).
457     *
458     * @param elements the elements to add to the {@code ImmutableSortedSet}
459     * @return this {@code Builder} object
460     * @throws NullPointerException if {@code elements} contains a null element
461     */
462    @CanIgnoreReturnValue
463    @Override
464    public Builder<E> addAll(Iterable<? extends E> elements) {
465      super.addAll(elements);
466      return this;
467    }
468
469    /**
470     * Adds each element of {@code elements} to the {@code ImmutableSortedSet}, ignoring duplicate
471     * elements (only the first duplicate element is added).
472     *
473     * @param elements the elements to add to the {@code ImmutableSortedSet}
474     * @return this {@code Builder} object
475     * @throws NullPointerException if {@code elements} contains a null element
476     */
477    @CanIgnoreReturnValue
478    @Override
479    public Builder<E> addAll(Iterator<? extends E> elements) {
480      super.addAll(elements);
481      return this;
482    }
483
484    @CanIgnoreReturnValue
485    @Override
486    Builder<E> combine(ImmutableSet.Builder<E> builder) {
487      super.combine(builder);
488      return this;
489    }
490
491    /**
492     * Returns a newly-created {@code ImmutableSortedSet} based on the contents of the {@code
493     * Builder} and its comparator.
494     */
495    @Override
496    public ImmutableSortedSet<E> build() {
497      @SuppressWarnings("unchecked") // we're careful to put only E's in here
498      E[] contentsArray = (E[]) contents;
499      ImmutableSortedSet<E> result = construct(comparator, size, contentsArray);
500      this.size = result.size(); // we eliminated duplicates in-place in contentsArray
501      this.forceCopy = true;
502      return result;
503    }
504  }
505
506  int unsafeCompare(Object a, Object b) {
507    return unsafeCompare(comparator, a, b);
508  }
509
510  static int unsafeCompare(Comparator<?> comparator, Object a, Object b) {
511    // Pretend the comparator can compare anything. If it turns out it can't
512    // compare a and b, we should get a CCE on the subsequent line. Only methods
513    // that are spec'd to throw CCE should call this.
514    @SuppressWarnings("unchecked")
515    Comparator<Object> unsafeComparator = (Comparator<Object>) comparator;
516    return unsafeComparator.compare(a, b);
517  }
518
519  final transient Comparator<? super E> comparator;
520
521  ImmutableSortedSet(Comparator<? super E> comparator) {
522    this.comparator = comparator;
523  }
524
525  /**
526   * Returns the comparator that orders the elements, which is {@link Ordering#natural()} when the
527   * natural ordering of the elements is used. Note that its behavior is not consistent with {@link
528   * SortedSet#comparator()}, which returns {@code null} to indicate natural ordering.
529   */
530  @Override
531  public Comparator<? super E> comparator() {
532    return comparator;
533  }
534
535  @Override // needed to unify the iterator() methods in Collection and SortedIterable
536  public abstract UnmodifiableIterator<E> iterator();
537
538  /**
539   * {@inheritDoc}
540   *
541   * <p>This method returns a serializable {@code ImmutableSortedSet}.
542   *
543   * <p>The {@link SortedSet#headSet} documentation states that a subset of a subset throws an
544   * {@link IllegalArgumentException} if passed a {@code toElement} greater than an earlier {@code
545   * toElement}. However, this method doesn't throw an exception in that situation, but instead
546   * keeps the original {@code toElement}.
547   */
548  @Override
549  public ImmutableSortedSet<E> headSet(E toElement) {
550    return headSet(toElement, false);
551  }
552
553  /** @since 12.0 */
554  @Override
555  public ImmutableSortedSet<E> headSet(E toElement, boolean inclusive) {
556    return headSetImpl(checkNotNull(toElement), inclusive);
557  }
558
559  /**
560   * {@inheritDoc}
561   *
562   * <p>This method returns a serializable {@code ImmutableSortedSet}.
563   *
564   * <p>The {@link SortedSet#subSet} documentation states that a subset of a subset throws an {@link
565   * IllegalArgumentException} if passed a {@code fromElement} smaller than an earlier {@code
566   * fromElement}. However, this method doesn't throw an exception in that situation, but instead
567   * keeps the original {@code fromElement}. Similarly, this method keeps the original {@code
568   * toElement}, instead of throwing an exception, if passed a {@code toElement} greater than an
569   * earlier {@code toElement}.
570   */
571  @Override
572  public ImmutableSortedSet<E> subSet(E fromElement, E toElement) {
573    return subSet(fromElement, true, toElement, false);
574  }
575
576  /** @since 12.0 */
577  @GwtIncompatible // NavigableSet
578  @Override
579  public ImmutableSortedSet<E> subSet(
580      E fromElement, boolean fromInclusive, E toElement, boolean toInclusive) {
581    checkNotNull(fromElement);
582    checkNotNull(toElement);
583    checkArgument(comparator.compare(fromElement, toElement) <= 0);
584    return subSetImpl(fromElement, fromInclusive, toElement, toInclusive);
585  }
586
587  /**
588   * {@inheritDoc}
589   *
590   * <p>This method returns a serializable {@code ImmutableSortedSet}.
591   *
592   * <p>The {@link SortedSet#tailSet} documentation states that a subset of a subset throws an
593   * {@link IllegalArgumentException} if passed a {@code fromElement} smaller than an earlier {@code
594   * fromElement}. However, this method doesn't throw an exception in that situation, but instead
595   * keeps the original {@code fromElement}.
596   */
597  @Override
598  public ImmutableSortedSet<E> tailSet(E fromElement) {
599    return tailSet(fromElement, true);
600  }
601
602  /** @since 12.0 */
603  @Override
604  public ImmutableSortedSet<E> tailSet(E fromElement, boolean inclusive) {
605    return tailSetImpl(checkNotNull(fromElement), inclusive);
606  }
607
608  /*
609   * These methods perform most headSet, subSet, and tailSet logic, besides
610   * parameter validation.
611   */
612  abstract ImmutableSortedSet<E> headSetImpl(E toElement, boolean inclusive);
613
614  abstract ImmutableSortedSet<E> subSetImpl(
615      E fromElement, boolean fromInclusive, E toElement, boolean toInclusive);
616
617  abstract ImmutableSortedSet<E> tailSetImpl(E fromElement, boolean inclusive);
618
619  /** @since 12.0 */
620  @GwtIncompatible // NavigableSet
621  @Override
622  public E lower(E e) {
623    return Iterators.getNext(headSet(e, false).descendingIterator(), null);
624  }
625
626  /** @since 12.0 */
627  @Override
628  public E floor(E e) {
629    return Iterators.getNext(headSet(e, true).descendingIterator(), null);
630  }
631
632  /** @since 12.0 */
633  @Override
634  public E ceiling(E e) {
635    return Iterables.getFirst(tailSet(e, true), null);
636  }
637
638  /** @since 12.0 */
639  @GwtIncompatible // NavigableSet
640  @Override
641  public E higher(E e) {
642    return Iterables.getFirst(tailSet(e, false), null);
643  }
644
645  @Override
646  public E first() {
647    return iterator().next();
648  }
649
650  @Override
651  public E last() {
652    return descendingIterator().next();
653  }
654
655  /**
656   * Guaranteed to throw an exception and leave the set unmodified.
657   *
658   * @since 12.0
659   * @throws UnsupportedOperationException always
660   * @deprecated Unsupported operation.
661   */
662  @CanIgnoreReturnValue
663  @Deprecated
664  @GwtIncompatible // NavigableSet
665  @Override
666  @DoNotCall("Always throws UnsupportedOperationException")
667  public final E pollFirst() {
668    throw new UnsupportedOperationException();
669  }
670
671  /**
672   * Guaranteed to throw an exception and leave the set unmodified.
673   *
674   * @since 12.0
675   * @throws UnsupportedOperationException always
676   * @deprecated Unsupported operation.
677   */
678  @CanIgnoreReturnValue
679  @Deprecated
680  @GwtIncompatible // NavigableSet
681  @Override
682  @DoNotCall("Always throws UnsupportedOperationException")
683  public final E pollLast() {
684    throw new UnsupportedOperationException();
685  }
686
687  @GwtIncompatible // NavigableSet
688  @LazyInit
689  transient ImmutableSortedSet<E> descendingSet;
690
691  /** @since 12.0 */
692  @GwtIncompatible // NavigableSet
693  @Override
694  public ImmutableSortedSet<E> descendingSet() {
695    // racy single-check idiom
696    ImmutableSortedSet<E> result = descendingSet;
697    if (result == null) {
698      result = descendingSet = createDescendingSet();
699      result.descendingSet = this;
700    }
701    return result;
702  }
703
704  // Most classes should implement this as new DescendingImmutableSortedSet<E>(this),
705  // but we push down that implementation because ProGuard can't eliminate it even when it's always
706  // overridden.
707  @GwtIncompatible // NavigableSet
708  abstract ImmutableSortedSet<E> createDescendingSet();
709
710  /** @since 12.0 */
711  @GwtIncompatible // NavigableSet
712  @Override
713  public abstract UnmodifiableIterator<E> descendingIterator();
714
715  /** Returns the position of an element within the set, or -1 if not present. */
716  abstract int indexOf(@NullableDecl Object target);
717
718  /*
719   * This class is used to serialize all ImmutableSortedSet instances,
720   * regardless of implementation type. It captures their "logical contents"
721   * only. This is necessary to ensure that the existence of a particular
722   * implementation type is an implementation detail.
723   */
724  private static class SerializedForm<E> implements Serializable {
725    final Comparator<? super E> comparator;
726    final Object[] elements;
727
728    public SerializedForm(Comparator<? super E> comparator, Object[] elements) {
729      this.comparator = comparator;
730      this.elements = elements;
731    }
732
733    @SuppressWarnings("unchecked")
734    Object readResolve() {
735      return new Builder<E>(comparator).add((E[]) elements).build();
736    }
737
738    private static final long serialVersionUID = 0;
739  }
740
741  private void readObject(ObjectInputStream unused) throws InvalidObjectException {
742    throw new InvalidObjectException("Use SerializedForm");
743  }
744
745  @Override
746  Object writeReplace() {
747    return new SerializedForm<E>(comparator, toArray());
748  }
749}