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    
017    package com.google.common.collect;
018    
019    import static com.google.common.base.Preconditions.checkArgument;
020    import static com.google.common.base.Preconditions.checkNotNull;
021    
022    import com.google.common.annotations.GwtCompatible;
023    import com.google.common.annotations.GwtIncompatible;
024    
025    import java.io.InvalidObjectException;
026    import java.io.ObjectInputStream;
027    import java.io.Serializable;
028    import java.util.ArrayList;
029    import java.util.Arrays;
030    import java.util.Collection;
031    import java.util.Collections;
032    import java.util.Comparator;
033    import java.util.Iterator;
034    import java.util.List;
035    import java.util.SortedSet;
036    
037    import javax.annotation.Nullable;
038    
039    /**
040     * An immutable {@code SortedSet} that stores its elements in a sorted array.
041     * Some instances are ordered by an explicit comparator, while others follow the
042     * natural sort ordering of their elements. Either way, null elements are not
043     * supported.
044     *
045     * <p>Unlike {@link Collections#unmodifiableSortedSet}, which is a <i>view</i>
046     * of a separate collection that can still change, an instance of {@code
047     * ImmutableSortedSet} contains its own private data and will <i>never</i>
048     * change. This class is convenient for {@code public static final} sets
049     * ("constant sets") and also lets you easily make a "defensive copy" of a set
050     * provided to your class by a caller.
051     *
052     * <p>The sets returned by the {@link #headSet}, {@link #tailSet}, and
053     * {@link #subSet} methods share the same array as the original set, preventing
054     * that array from being garbage collected. If this is a concern, the data may
055     * be copied into a correctly-sized array by calling {@link #copyOfSorted}.
056     *
057     * <p><b>Note on element equivalence:</b> The {@link #contains(Object)},
058     * {@link #containsAll(Collection)}, and {@link #equals(Object)}
059     * implementations must check whether a provided object is equivalent to an
060     * element in the collection. Unlike most collections, an
061     * {@code ImmutableSortedSet} doesn't use {@link Object#equals} to determine if
062     * two elements are equivalent. Instead, with an explicit comparator, the
063     * following relation determines whether elements {@code x} and {@code y} are
064     * equivalent: <pre>   {@code
065     *
066     *   {(x, y) | comparator.compare(x, y) == 0}}</pre>
067     *
068     * With natural ordering of elements, the following relation determines whether
069     * two elements are equivalent: <pre>   {@code
070     *
071     *   {(x, y) | x.compareTo(y) == 0}}</pre>
072     *
073     * <b>Warning:</b> Like most sets, an {@code ImmutableSortedSet} will not
074     * function correctly if an element is modified after being placed in the set.
075     * For this reason, and to avoid general confusion, it is strongly recommended
076     * to place only immutable objects into this collection.
077     *
078     * <p><b>Note:</b> Although this class is not final, it cannot be subclassed as
079     * it has no public or protected constructors. Thus, instances of this type are
080     * guaranteed to be immutable.
081     *
082     * <p>See the Guava User Guide article on <a href=
083     * "http://code.google.com/p/guava-libraries/wiki/ImmutableCollectionsExplained">
084     * immutable collections</a>.
085     *
086     * @see ImmutableSet
087     * @author Jared Levy
088     * @author Louis Wasserman
089     * @since 2.0 (imported from Google Collections Library; implements {@code NavigableSet} since 12.0)
090     */
091    // TODO(benyu): benchmark and optimize all creation paths, which are a mess now
092    @GwtCompatible(serializable = true, emulated = true)
093    @SuppressWarnings("serial") // we're overriding default serialization
094    public abstract class ImmutableSortedSet<E> extends ImmutableSortedSetFauxverideShim<E>
095        implements SortedSet<E>, SortedIterable<E> {
096    
097      private static final Comparator<Comparable> NATURAL_ORDER =
098          Ordering.natural();
099    
100      private static final ImmutableSortedSet<Comparable> NATURAL_EMPTY_SET =
101          new EmptyImmutableSortedSet<Comparable>(NATURAL_ORDER);
102    
103      @SuppressWarnings("unchecked")
104      private static <E> ImmutableSortedSet<E> emptySet() {
105        return (ImmutableSortedSet<E>) NATURAL_EMPTY_SET;
106      }
107    
108      static <E> ImmutableSortedSet<E> emptySet(
109          Comparator<? super E> comparator) {
110        if (NATURAL_ORDER.equals(comparator)) {
111          return emptySet();
112        } else {
113          return new EmptyImmutableSortedSet<E>(comparator);
114        }
115      }
116    
117      /**
118       * Returns the empty immutable sorted set.
119       */
120      public static <E> ImmutableSortedSet<E> of() {
121        return emptySet();
122      }
123    
124      /**
125       * Returns an immutable sorted set containing a single element.
126       */
127      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
128          E element) {
129        return new RegularImmutableSortedSet<E>(
130            ImmutableList.of(element), Ordering.natural());
131      }
132    
133      /**
134       * Returns an immutable sorted set containing the given elements sorted by
135       * their natural ordering. When multiple elements are equivalent according to
136       * {@link Comparable#compareTo}, only the first one specified is included.
137       *
138       * @throws NullPointerException if any element is null
139       */
140      @SuppressWarnings("unchecked")
141      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
142          E e1, E e2) {
143        return copyOf(Ordering.natural(), Arrays.asList(e1, e2));
144      }
145    
146      /**
147       * Returns an immutable sorted set containing the given elements sorted by
148       * their natural ordering. When multiple elements are equivalent according to
149       * {@link Comparable#compareTo}, only the first one specified is included.
150       *
151       * @throws NullPointerException if any element is null
152       */
153      @SuppressWarnings("unchecked")
154      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
155          E e1, E e2, E e3) {
156        return copyOf(Ordering.natural(), Arrays.asList(e1, e2, e3));
157      }
158    
159      /**
160       * Returns an immutable sorted set containing the given elements sorted by
161       * their natural ordering. When multiple elements are equivalent according to
162       * {@link Comparable#compareTo}, only the first one specified is included.
163       *
164       * @throws NullPointerException if any element is null
165       */
166      @SuppressWarnings("unchecked")
167      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
168          E e1, E e2, E e3, E e4) {
169        return copyOf(Ordering.natural(), Arrays.asList(e1, e2, e3, e4));
170      }
171    
172      /**
173       * Returns an immutable sorted set containing the given elements sorted by
174       * their natural ordering. When multiple elements are equivalent according to
175       * {@link Comparable#compareTo}, only the first one specified is included.
176       *
177       * @throws NullPointerException if any element is null
178       */
179      @SuppressWarnings("unchecked")
180      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
181          E e1, E e2, E e3, E e4, E e5) {
182        return copyOf(Ordering.natural(), Arrays.asList(e1, e2, e3, e4, e5));
183      }
184    
185      /**
186       * Returns an immutable sorted set containing the given elements sorted by
187       * their natural ordering. When multiple elements are equivalent according to
188       * {@link Comparable#compareTo}, only the first one specified is included.
189       *
190       * @throws NullPointerException if any element is null
191       * @since 3.0 (source-compatible since 2.0)
192       */
193      @SuppressWarnings("unchecked")
194      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> of(
195          E e1, E e2, E e3, E e4, E e5, E e6, E... remaining) {
196        int size = remaining.length + 6;
197        List<E> all = new ArrayList<E>(size);
198        Collections.addAll(all, e1, e2, e3, e4, e5, e6);
199        Collections.addAll(all, remaining);
200        return copyOf(Ordering.natural(), all);
201      }
202    
203      // TODO(kevinb): Consider factory methods that reject duplicates
204    
205      /**
206       * Returns an immutable sorted set containing the given elements sorted by
207       * their natural ordering. When multiple elements are equivalent according to
208       * {@link Comparable#compareTo}, only the first one specified is included.
209       *
210       * @throws NullPointerException if any of {@code elements} is null
211       * @since 3.0
212       */
213      public static <E extends Comparable<? super E>> ImmutableSortedSet<E> copyOf(
214          E[] elements) {
215        return copyOf(Ordering.natural(), Arrays.asList(elements));
216      }
217    
218      /**
219       * Returns an immutable sorted set containing the given elements sorted by
220       * their natural ordering. When multiple elements are equivalent according to
221       * {@code compareTo()}, only the first one specified is included. To create a
222       * copy of a {@code SortedSet} that preserves the comparator, call {@link
223       * #copyOfSorted} instead. This method iterates over {@code elements} at most
224       * once.
225    
226       *
227       * <p>Note that if {@code s} is a {@code Set<String>}, then {@code
228       * ImmutableSortedSet.copyOf(s)} returns an {@code ImmutableSortedSet<String>}
229       * containing each of the strings in {@code s}, while {@code
230       * ImmutableSortedSet.of(s)} returns an {@code
231       * ImmutableSortedSet<Set<String>>} containing one element (the given set
232       * itself).
233       *
234       * <p>Despite the method name, this method attempts to avoid actually copying
235       * the data when it is safe to do so. The exact circumstances under which a
236       * copy will or will not be performed are undocumented and subject to change.
237       *
238       * <p>This method is not type-safe, as it may be called on elements that are
239       * not mutually comparable.
240       *
241       * @throws ClassCastException if the elements are not mutually comparable
242       * @throws NullPointerException if any of {@code elements} is null
243       */
244      public static <E> ImmutableSortedSet<E> copyOf(
245          Iterable<? extends E> elements) {
246        // Hack around E not being a subtype of Comparable.
247        // Unsafe, see ImmutableSortedSetFauxverideShim.
248        @SuppressWarnings("unchecked")
249        Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
250        return copyOf(naturalOrder, elements);
251      }
252    
253      /**
254       * Returns an immutable sorted set containing the given elements sorted by
255       * their natural ordering. When multiple elements are equivalent according to
256       * {@code compareTo()}, only the first one specified is included. To create a
257       * copy of a {@code SortedSet} that preserves the comparator, call
258       * {@link #copyOfSorted} instead. This method iterates over {@code elements}
259       * at most once.
260       *
261       * <p>Note that if {@code s} is a {@code Set<String>}, then
262       * {@code ImmutableSortedSet.copyOf(s)} returns an
263       * {@code ImmutableSortedSet<String>} containing each of the strings in
264       * {@code s}, while {@code ImmutableSortedSet.of(s)} returns an
265       * {@code ImmutableSortedSet<Set<String>>} containing one element (the given
266       * set itself).
267       *
268       * <p><b>Note:</b> Despite what the method name suggests, if {@code elements}
269       * is an {@code ImmutableSortedSet}, it may be returned instead of a copy.
270       *
271       * <p>This method is not type-safe, as it may be called on elements that are
272       * not mutually comparable.
273       *
274       * <p>This method is safe to use even when {@code elements} is a synchronized
275       * or concurrent collection that is currently being modified by another
276       * thread.
277       *
278       * @throws ClassCastException if the elements are not mutually comparable
279       * @throws NullPointerException if any of {@code elements} is null
280       * @since 7.0 (source-compatible since 2.0)
281       */
282      public static <E> ImmutableSortedSet<E> copyOf(
283          Collection<? extends E> elements) {
284        // Hack around E not being a subtype of Comparable.
285        // Unsafe, see ImmutableSortedSetFauxverideShim.
286        @SuppressWarnings("unchecked")
287        Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
288        return copyOf(naturalOrder, elements);
289      }
290    
291      /**
292       * Returns an immutable sorted set containing the given elements sorted by
293       * their natural ordering. When multiple elements are equivalent according to
294       * {@code compareTo()}, only the first one specified is included.
295       *
296       * <p>This method is not type-safe, as it may be called on elements that are
297       * not mutually comparable.
298       *
299       * @throws ClassCastException if the elements are not mutually comparable
300       * @throws NullPointerException if any of {@code elements} is null
301       */
302      public static <E> ImmutableSortedSet<E> copyOf(
303          Iterator<? extends E> elements) {
304        // Hack around E not being a subtype of Comparable.
305        // Unsafe, see ImmutableSortedSetFauxverideShim.
306        @SuppressWarnings("unchecked")
307        Ordering<E> naturalOrder = (Ordering<E>) Ordering.<Comparable>natural();
308        return copyOf(naturalOrder, elements);
309      }
310    
311      /**
312       * Returns an immutable sorted set containing the given elements sorted by
313       * the given {@code Comparator}. When multiple elements are equivalent
314       * according to {@code compareTo()}, only the first one specified is
315       * included.
316       *
317       * @throws NullPointerException if {@code comparator} or any of
318       *     {@code elements} is null
319       */
320      public static <E> ImmutableSortedSet<E> copyOf(
321          Comparator<? super E> comparator, Iterator<? extends E> elements) {
322        return copyOf(comparator, Lists.newArrayList(elements));
323      }
324    
325      /**
326       * Returns an immutable sorted set containing the given elements sorted by
327       * the given {@code Comparator}. When multiple elements are equivalent
328       * according to {@code compare()}, only the first one specified is
329       * included. This method iterates over {@code elements} at most once.
330       *
331       * <p>Despite the method name, this method attempts to avoid actually copying
332       * the data when it is safe to do so. The exact circumstances under which a
333       * copy will or will not be performed are undocumented and subject to change.
334       *
335       * @throws NullPointerException if {@code comparator} or any of {@code
336       *         elements} is null
337       */
338      public static <E> ImmutableSortedSet<E> copyOf(
339          Comparator<? super E> comparator, Iterable<? extends E> elements) {
340        checkNotNull(comparator);
341        boolean hasSameComparator =
342            SortedIterables.hasSameComparator(comparator, elements);
343    
344        if (hasSameComparator && (elements instanceof ImmutableSortedSet)) {
345          @SuppressWarnings("unchecked")
346          ImmutableSortedSet<E> original = (ImmutableSortedSet<E>) elements;
347          if (!original.isPartialView()) {
348            return original;
349          }
350        }
351        @SuppressWarnings("unchecked") // elements only contains E's; it's safe.
352        E[] array = (E[]) Iterables.toArray(elements);
353        return construct(comparator, array.length, array);
354      }
355    
356      /**
357       * Returns an immutable sorted set containing the given elements sorted by
358       * the given {@code Comparator}. When multiple elements are equivalent
359       * according to {@code compareTo()}, only the first one specified is
360       * included.
361       *
362       * <p>Despite the method name, this method attempts to avoid actually copying
363       * the data when it is safe to do so. The exact circumstances under which a
364       * copy will or will not be performed are undocumented and subject to change.
365       *
366       * <p>This method is safe to use even when {@code elements} is a synchronized
367       * or concurrent collection that is currently being modified by another
368       * thread.
369       *
370       * @throws NullPointerException if {@code comparator} or any of
371       *     {@code elements} is null
372       * @since 7.0 (source-compatible since 2.0)
373       */
374      public static <E> ImmutableSortedSet<E> copyOf(
375          Comparator<? super E> comparator, Collection<? extends E> elements) {
376        return copyOf(comparator, (Iterable<? extends E>) elements);
377      }
378    
379      /**
380       * Returns an immutable sorted set containing the elements of a sorted set,
381       * sorted by the same {@code Comparator}. That behavior differs from {@link
382       * #copyOf(Iterable)}, which always uses the natural ordering of the
383       * elements.
384       *
385       * <p>Despite the method name, this method attempts to avoid actually copying
386       * the data when it is safe to do so. The exact circumstances under which a
387       * copy will or will not be performed are undocumented and subject to change.
388       *
389       * <p>This method is safe to use even when {@code sortedSet} is a synchronized
390       * or concurrent collection that is currently being modified by another
391       * thread.
392       *
393       * @throws NullPointerException if {@code sortedSet} or any of its elements
394       *     is null
395       */
396      public static <E> ImmutableSortedSet<E> copyOfSorted(SortedSet<E> sortedSet) {
397        Comparator<? super E> comparator = SortedIterables.comparator(sortedSet);
398        E[] elements = (E[]) sortedSet.toArray();
399        if (elements.length == 0) {
400          return emptySet(comparator);
401        } else {
402          return new RegularImmutableSortedSet<E>(
403              ImmutableList.<E>asImmutableList(elements), comparator);
404        }
405      }
406    
407      /**
408       * Sorts and eliminates duplicates from the first {@code n} positions in {@code contents}.
409       * Returns the number of unique elements.  If this returns {@code k}, then the first {@code k}
410       * elements of {@code contents} will be the sorted, unique elements, and {@code
411       * contents[i] == null} for {@code k <= i < n}.
412       *
413       * @throws NullPointerException if any of the first {@code n} elements of {@code contents} is
414       *          null
415       */
416      static <E> int sortAndUnique(
417          Comparator<? super E> comparator, int n, E... contents) {
418        if (n == 0) {
419          return 0;
420        }
421        for (int i = 0; i < n; i++) {
422          ObjectArrays.checkElementNotNull(contents[i], i);
423        }
424        Arrays.sort(contents, 0, n, comparator);
425        int uniques = 1;
426        for (int i = 1; i < n; i++) {
427          E cur = contents[i];
428          E prev = contents[uniques - 1];
429          if (comparator.compare(cur, prev) != 0) {
430            contents[uniques++] = cur;
431          }
432        }
433        Arrays.fill(contents, uniques, n, null);
434        return uniques;
435      }
436    
437      /**
438       * Constructs an {@code ImmutableSortedSet} from the first {@code n} elements of
439       * {@code contents}.  If {@code k} is the size of the returned {@code ImmutableSortedSet}, then
440       * the sorted unique elements are in the first {@code k} positions of {@code contents}, and
441       * {@code contents[i] == null} for {@code k <= i < n}.
442       *
443       * <p>If {@code k == contents.length}, then {@code contents} may no longer be safe for
444       * modification.
445       *
446       * @throws NullPointerException if any of the first {@code n} elements of {@code contents} is
447       *          null
448       */
449      static <E> ImmutableSortedSet<E> construct(
450          Comparator<? super E> comparator, int n, E... contents) {
451        int uniques = sortAndUnique(comparator, n, contents);
452        if (uniques == 0) {
453          return emptySet(comparator);
454        } else if (uniques < contents.length) {
455          contents = ObjectArrays.arraysCopyOf(contents, uniques);
456        }
457        return new RegularImmutableSortedSet<E>(
458            ImmutableList.<E>asImmutableList(contents), comparator);
459      }
460    
461      /**
462       * Returns a builder that creates immutable sorted sets with an explicit
463       * comparator. If the comparator has a more general type than the set being
464       * generated, such as creating a {@code SortedSet<Integer>} with a
465       * {@code Comparator<Number>}, use the {@link Builder} constructor instead.
466       *
467       * @throws NullPointerException if {@code comparator} is null
468       */
469      public static <E> Builder<E> orderedBy(Comparator<E> comparator) {
470        return new Builder<E>(comparator);
471      }
472    
473      /**
474       * Returns a builder that creates immutable sorted sets whose elements are
475       * ordered by the reverse of their natural ordering.
476       *
477       * <p>Note: the type parameter {@code E} extends {@code Comparable<E>} rather
478       * than {@code Comparable<? super E>} as a workaround for javac <a
479       * href="http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6468354">bug
480       * 6468354</a>.
481       */
482      public static <E extends Comparable<E>> Builder<E> reverseOrder() {
483        return new Builder<E>(Ordering.natural().reverse());
484      }
485    
486      /**
487       * Returns a builder that creates immutable sorted sets whose elements are
488       * ordered by their natural ordering. The sorted sets use {@link
489       * Ordering#natural()} as the comparator. This method provides more
490       * type-safety than {@link #builder}, as it can be called only for classes
491       * that implement {@link Comparable}.
492       *
493       * <p>Note: the type parameter {@code E} extends {@code Comparable<E>} rather
494       * than {@code Comparable<? super E>} as a workaround for javac <a
495       * href="http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6468354">bug
496       * 6468354</a>.
497       */
498      public static <E extends Comparable<E>> Builder<E> naturalOrder() {
499        return new Builder<E>(Ordering.natural());
500      }
501    
502      /**
503       * A builder for creating immutable sorted set instances, especially {@code
504       * public static final} sets ("constant sets"), with a given comparator.
505       * Example: <pre>   {@code
506       *
507       *   public static final ImmutableSortedSet<Number> LUCKY_NUMBERS =
508       *       new ImmutableSortedSet.Builder<Number>(ODDS_FIRST_COMPARATOR)
509       *           .addAll(SINGLE_DIGIT_PRIMES)
510       *           .add(42)
511       *           .build();}</pre>
512       *
513       * Builder instances can be reused; it is safe to call {@link #build} multiple
514       * times to build multiple sets in series. Each set is a superset of the set
515       * created before it.
516       *
517       * @since 2.0 (imported from Google Collections Library)
518       */
519      public static final class Builder<E> extends ImmutableSet.Builder<E> {
520        private final Comparator<? super E> comparator;
521    
522        /**
523         * Creates a new builder. The returned builder is equivalent to the builder
524         * generated by {@link ImmutableSortedSet#orderedBy}.
525         */
526        public Builder(Comparator<? super E> comparator) {
527          this.comparator = checkNotNull(comparator);
528        }
529    
530        /**
531         * Adds {@code element} to the {@code ImmutableSortedSet}.  If the
532         * {@code ImmutableSortedSet} already contains {@code element}, then
533         * {@code add} has no effect. (only the previously added element
534         * is retained).
535         *
536         * @param element the element to add
537         * @return this {@code Builder} object
538         * @throws NullPointerException if {@code element} is null
539         */
540        
541        @Override
542        public Builder<E> add(E element) {
543          super.add(element);
544          return this;
545        }
546    
547        /**
548         * Adds each element of {@code elements} to the {@code ImmutableSortedSet},
549         * ignoring duplicate elements (only the first duplicate element is added).
550         *
551         * @param elements the elements to add
552         * @return this {@code Builder} object
553         * @throws NullPointerException if {@code elements} contains a null element
554         */
555        
556        @Override
557        public Builder<E> add(E... elements) {
558          super.add(elements);
559          return this;
560        }
561    
562        /**
563         * Adds each element of {@code elements} to the {@code ImmutableSortedSet},
564         * ignoring duplicate elements (only the first duplicate element is added).
565         *
566         * @param elements the elements to add to the {@code ImmutableSortedSet}
567         * @return this {@code Builder} object
568         * @throws NullPointerException if {@code elements} contains a null element
569         */
570        
571        @Override
572        public Builder<E> addAll(Iterable<? extends E> elements) {
573          super.addAll(elements);
574          return this;
575        }
576    
577        /**
578         * Adds each element of {@code elements} to the {@code ImmutableSortedSet},
579         * ignoring duplicate elements (only the first duplicate element is added).
580         *
581         * @param elements the elements to add to the {@code ImmutableSortedSet}
582         * @return this {@code Builder} object
583         * @throws NullPointerException if {@code elements} contains a null element
584         */
585        
586        @Override
587        public Builder<E> addAll(Iterator<? extends E> elements) {
588          super.addAll(elements);
589          return this;
590        }
591    
592        /**
593         * Returns a newly-created {@code ImmutableSortedSet} based on the contents
594         * of the {@code Builder} and its comparator.
595         */
596        @Override
597        public ImmutableSortedSet<E> build() {
598          @SuppressWarnings("unchecked") // we're careful to put only E's in here
599          E[] contentsArray = (E[]) contents;
600          ImmutableSortedSet<E> result = construct(comparator, size, contentsArray);
601          this.size = result.size(); // we eliminated duplicates in-place in contentsArray
602          return result;
603        }
604      }
605    
606      int unsafeCompare(Object a, Object b) {
607        return unsafeCompare(comparator, a, b);
608      }
609    
610      static int unsafeCompare(
611          Comparator<?> comparator, Object a, Object b) {
612        // Pretend the comparator can compare anything. If it turns out it can't
613        // compare a and b, we should get a CCE on the subsequent line. Only methods
614        // that are spec'd to throw CCE should call this.
615        @SuppressWarnings("unchecked")
616        Comparator<Object> unsafeComparator = (Comparator<Object>) comparator;
617        return unsafeComparator.compare(a, b);
618      }
619    
620      final transient Comparator<? super E> comparator;
621    
622      ImmutableSortedSet(Comparator<? super E> comparator) {
623        this.comparator = comparator;
624      }
625    
626      /**
627       * Returns the comparator that orders the elements, which is
628       * {@link Ordering#natural()} when the natural ordering of the
629       * elements is used. Note that its behavior is not consistent with
630       * {@link SortedSet#comparator()}, which returns {@code null} to indicate
631       * natural ordering.
632       */
633      public Comparator<? super E> comparator() {
634        return comparator;
635      }
636    
637      // needed to unify the iterator() methods in Collection and SortedIterable
638      
639      @Override
640      public abstract UnmodifiableIterator<E> iterator();
641    
642      /**
643       * {@inheritDoc}
644       *
645       * <p>This method returns a serializable {@code ImmutableSortedSet}.
646       *
647       * <p>The {@link SortedSet#headSet} documentation states that a subset of a
648       * subset throws an {@link IllegalArgumentException} if passed a
649       * {@code toElement} greater than an earlier {@code toElement}. However, this
650       * method doesn't throw an exception in that situation, but instead keeps the
651       * original {@code toElement}.
652       */
653      public ImmutableSortedSet<E> headSet(E toElement) {
654        return headSet(toElement, false);
655      }
656    
657      /**
658       * @since 12.0
659       */
660      @GwtIncompatible("NavigableSet")
661      public ImmutableSortedSet<E> headSet(E toElement, boolean inclusive) {
662        return headSetImpl(checkNotNull(toElement), inclusive);
663      }
664    
665      /**
666       * {@inheritDoc}
667       *
668       * <p>This method returns a serializable {@code ImmutableSortedSet}.
669       *
670       * <p>The {@link SortedSet#subSet} documentation states that a subset of a
671       * subset throws an {@link IllegalArgumentException} if passed a
672       * {@code fromElement} smaller than an earlier {@code fromElement}. However,
673       * this method doesn't throw an exception in that situation, but instead keeps
674       * the original {@code fromElement}. Similarly, this method keeps the
675       * original {@code toElement}, instead of throwing an exception, if passed a
676       * {@code toElement} greater than an earlier {@code toElement}.
677       */
678      public ImmutableSortedSet<E> subSet(E fromElement, E toElement) {
679        return subSet(fromElement, true, toElement, false);
680      }
681    
682      /**
683       * @since 12.0
684       */
685      @GwtIncompatible("NavigableSet")
686      public ImmutableSortedSet<E> subSet(
687          E fromElement, boolean fromInclusive, E toElement, boolean toInclusive) {
688        checkNotNull(fromElement);
689        checkNotNull(toElement);
690        checkArgument(comparator.compare(fromElement, toElement) <= 0);
691        return subSetImpl(fromElement, fromInclusive, toElement, toInclusive);
692      }
693    
694      /**
695       * {@inheritDoc}
696       *
697       * <p>This method returns a serializable {@code ImmutableSortedSet}.
698       *
699       * <p>The {@link SortedSet#tailSet} documentation states that a subset of a
700       * subset throws an {@link IllegalArgumentException} if passed a
701       * {@code fromElement} smaller than an earlier {@code fromElement}. However,
702       * this method doesn't throw an exception in that situation, but instead keeps
703       * the original {@code fromElement}.
704       */
705      public ImmutableSortedSet<E> tailSet(E fromElement) {
706        return tailSet(fromElement, true);
707      }
708    
709      /**
710       * @since 12.0
711       */
712      @GwtIncompatible("NavigableSet")
713      public ImmutableSortedSet<E> tailSet(E fromElement, boolean inclusive) {
714        return tailSetImpl(checkNotNull(fromElement), inclusive);
715      }
716    
717      /*
718       * These methods perform most headSet, subSet, and tailSet logic, besides
719       * parameter validation.
720       */
721      abstract ImmutableSortedSet<E> headSetImpl(E toElement, boolean inclusive);
722    
723      abstract ImmutableSortedSet<E> subSetImpl(
724          E fromElement, boolean fromInclusive, E toElement, boolean toInclusive);
725    
726      abstract ImmutableSortedSet<E> tailSetImpl(E fromElement, boolean inclusive);
727    
728      /**
729       * @since 12.0
730       */
731      @GwtIncompatible("NavigableSet")
732      public E lower(E e) {
733        return Iterables.getFirst(headSet(e, false).descendingSet(), null);
734      }
735    
736      /**
737       * @since 12.0
738       */
739      @GwtIncompatible("NavigableSet")
740      public E floor(E e) {
741        return Iterables.getFirst(headSet(e, true).descendingSet(), null);
742      }
743    
744      /**
745       * @since 12.0
746       */
747      @GwtIncompatible("NavigableSet")
748      public E ceiling(E e) {
749        return Iterables.getFirst(tailSet(e, true), null);
750      }
751    
752      /**
753       * @since 12.0
754       */
755      @GwtIncompatible("NavigableSet")
756      public E higher(E e) {
757        return Iterables.getFirst(tailSet(e, false), null);
758      }
759    
760      /**
761       * @since 12.0
762       */
763      @GwtIncompatible("NavigableSet")
764      public final E pollFirst() {
765        throw new UnsupportedOperationException();
766      }
767    
768      /**
769       * @since 12.0
770       */
771      @GwtIncompatible("NavigableSet")
772      public final E pollLast() {
773        throw new UnsupportedOperationException();
774      }
775    
776      @GwtIncompatible("NavigableSet")
777      transient ImmutableSortedSet<E> descendingSet;
778    
779      /**
780       * @since 12.0
781       */
782      @GwtIncompatible("NavigableSet")
783      public ImmutableSortedSet<E> descendingSet() {
784        ImmutableSortedSet<E> result = descendingSet;
785        if (result == null) {
786          result = descendingSet = createDescendingSet();
787          result.descendingSet = this;
788        }
789        return result;
790      }
791    
792      @GwtIncompatible("NavigableSet")
793      abstract ImmutableSortedSet<E> createDescendingSet();
794    
795      /**
796       * @since 12.0
797       */
798      @GwtIncompatible("NavigableSet")
799      public UnmodifiableIterator<E> descendingIterator() {
800        return descendingSet().iterator();
801      }
802    
803      /**
804       * Returns the position of an element within the set, or -1 if not present.
805       */
806      abstract int indexOf(@Nullable Object target);
807    
808      /*
809       * This class is used to serialize all ImmutableSortedSet instances,
810       * regardless of implementation type. It captures their "logical contents"
811       * only. This is necessary to ensure that the existence of a particular
812       * implementation type is an implementation detail.
813       */
814      private static class SerializedForm<E> implements Serializable {
815        final Comparator<? super E> comparator;
816        final Object[] elements;
817    
818        public SerializedForm(Comparator<? super E> comparator, Object[] elements) {
819          this.comparator = comparator;
820          this.elements = elements;
821        }
822    
823        @SuppressWarnings("unchecked")
824        Object readResolve() {
825          return new Builder<E>(comparator).add((E[]) elements).build();
826        }
827    
828        private static final long serialVersionUID = 0;
829      }
830    
831      private void readObject(ObjectInputStream stream)
832          throws InvalidObjectException {
833        throw new InvalidObjectException("Use SerializedForm");
834      }
835    
836      
837      @Override
838      Object writeReplace() {
839        return new SerializedForm<E>(comparator, toArray());
840      }
841    }
842