/*
* Copyright (C) 2007 The Guava Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.glassfish.jersey.internal.guava;
import java.util.Collections;
import java.util.Comparator;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.function.Function;
A comparator, with additional methods to support common operations. This is an "enriched" version of Comparator
, in the same sense that FluentIterable
is an enriched Iterable
.
The common ways to get an instance of Ordering
are:
- Subclass it and implement
compare
instead of implementing Comparator
directly - Pass a pre-existing
Comparator
instance to from(Comparator<Object>)
- Use the natural ordering,
natural
Then you can use the chaining methods to get an altered version of that Ordering
, including:
reverse
compound(Comparator)
onResultOf(Function)
nullsFirst
/ nullsLast
Finally, use the resulting Ordering
anywhere a Comparator
is required, or use any of its special operations, such as:
Except as noted, the orderings returned by the factory methods of this class are serializable if and only if the provided instances that back them are. For example, if ordering
and function
can themselves be serialized, then ordering.onResultOf(function)
can as well.
See the Guava User Guide article on Ordering
.
Author: Jesse Wilson, Kevin Bourrillion Since: 2.0 (imported from Google Collections Library)
/**
* A comparator, with additional methods to support common operations. This is
* an "enriched" version of {@code Comparator}, in the same sense that {@link
* FluentIterable} is an enriched {@link Iterable}.
* <p>
* <p>The common ways to get an instance of {@code Ordering} are:
* <p>
* <ul>
* <li>Subclass it and implement {@link #compare} instead of implementing
* {@link Comparator} directly
* <li>Pass a <i>pre-existing</i> {@link Comparator} instance to {@link
* #from(Comparator)}
* <li>Use the natural ordering, {@link Ordering#natural}
* </ul>
* <p>
* <p>Then you can use the <i>chaining</i> methods to get an altered version of
* that {@code Ordering}, including:
* <p>
* <ul>
* <li>{@link #reverse}
* <li>{@link #compound(Comparator)}
* <li>{@link #onResultOf(Function)}
* <li>{@link #nullsFirst} / {@link #nullsLast}
* </ul>
* <p>
* <p>Finally, use the resulting {@code Ordering} anywhere a {@link Comparator}
* is required, or use any of its special operations, such as:</p>
* <p>
* <ul>
* <li>{@link #immutableSortedCopy}
* <li>{@link #isOrdered} / {@link #isStrictlyOrdered}
* <li>{@link #min} / {@link #max}
* </ul>
* <p>
* <p>Except as noted, the orderings returned by the factory methods of this
* class are serializable if and only if the provided instances that back them
* are. For example, if {@code ordering} and {@code function} can themselves be
* serialized, then {@code ordering.onResultOf(function)} can as well.
* <p>
* <p>See the Guava User Guide article on <a href=
* "http://code.google.com/p/guava-libraries/wiki/OrderingExplained">
* {@code Ordering}</a>.
*
* @author Jesse Wilson
* @author Kevin Bourrillion
* @since 2.0 (imported from Google Collections Library)
*/
public abstract class Ordering<T> implements Comparator<T> {
// Natural order
// Never make these public
static final int LEFT_IS_GREATER = 1;
// Static factories
static final int RIGHT_IS_GREATER = -1;
Constructs a new instance of this class (only invokable by the subclass
constructor, typically implicit).
/**
* Constructs a new instance of this class (only invokable by the subclass
* constructor, typically implicit).
*/
Ordering() {
}
// Instance-based factories (and any static equivalents)
Returns a serializable ordering that uses the natural order of the values. The ordering throws a NullPointerException
when passed a null parameter.
The type specification is <C extends Comparable>
, instead of the technically correct <C extends Comparable<? super C>>
, to support legacy types from before Java 5.
/**
* Returns a serializable ordering that uses the natural order of the values.
* The ordering throws a {@link NullPointerException} when passed a null
* parameter.
* <p>
* <p>The type specification is {@code <C extends Comparable>}, instead of
* the technically correct {@code <C extends Comparable<? super C>>}, to
* support legacy types from before Java 5.
*/
@SuppressWarnings("unchecked") // TODO(kevinb): right way to explain this??
public static <C extends Comparable> Ordering<C> natural() {
return (Ordering<C>) NaturalOrdering.INSTANCE;
}
Returns an ordering based on an existing comparator instance. Note
that it is unnecessary to create a new anonymous inner class implementing Comparator
just to pass it in here. Instead, simply subclass Ordering
and implement its compare
method directly. Params: - comparator – the comparator that defines the order
Returns: comparator itself if it is already an Ordering
; otherwise an ordering that wraps that comparator
/**
* Returns an ordering based on an <i>existing</i> comparator instance. Note
* that it is unnecessary to create a <i>new</i> anonymous inner class
* implementing {@code Comparator} just to pass it in here. Instead, simply
* subclass {@code Ordering} and implement its {@code compare} method
* directly.
*
* @param comparator the comparator that defines the order
* @return comparator itself if it is already an {@code Ordering}; otherwise
* an ordering that wraps that comparator
*/
public static <T> Ordering<T> from(Comparator<T> comparator) {
return (comparator instanceof Ordering)
? (Ordering<T>) comparator
: new ComparatorOrdering<T>(comparator);
}
Returns the reverse of this ordering; the Ordering
equivalent to Collections.reverseOrder(Comparator<Object>)
. /**
* Returns the reverse of this ordering; the {@code Ordering} equivalent to
* {@link Collections#reverseOrder(Comparator)}.
*/
// type parameter <S> lets us avoid the extra <String> in statements like:
// Ordering<String> o = Ordering.<String>natural().reverse();
public <S extends T> Ordering<S> reverse() {
return new ReverseOrdering<S>(this);
}
Returns an ordering that treats null
as less than all other values and uses this
to compare non-null values. /**
* Returns an ordering that treats {@code null} as less than all other values
* and uses {@code this} to compare non-null values.
*/
// type parameter <S> lets us avoid the extra <String> in statements like:
// Ordering<String> o = Ordering.<String>natural().nullsFirst();
<S extends T> Ordering<S> nullsFirst() {
return new NullsFirstOrdering<S>(this);
}
Returns an ordering that treats null
as greater than all other values and uses this ordering to compare non-null values. /**
* Returns an ordering that treats {@code null} as greater than all other
* values and uses this ordering to compare non-null values.
*/
// type parameter <S> lets us avoid the extra <String> in statements like:
// Ordering<String> o = Ordering.<String>natural().nullsLast();
<S extends T> Ordering<S> nullsLast() {
return new NullsLastOrdering<S>(this);
}
// Regular instance methods
// Override to add @Nullable
@Override
public abstract int compare(T left, T right);
Returns the least of the specified values according to this ordering. If there are multiple least values, the first of those is returned. The iterator will be left exhausted: its hasNext()
method will return false
. Params: - iterator – the iterator whose minimum element is to be determined
Throws: - NoSuchElementException – if
iterator
is empty - ClassCastException – if the parameters are not mutually
comparable under this ordering.
Since: 11.0
/**
* Returns the least of the specified values according to this ordering. If
* there are multiple least values, the first of those is returned. The
* iterator will be left exhausted: its {@code hasNext()} method will return
* {@code false}.
*
* @param iterator the iterator whose minimum element is to be determined
* @throws NoSuchElementException if {@code iterator} is empty
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
* @since 11.0
*/
<E extends T> E min(Iterator<E> iterator) {
// let this throw NoSuchElementException as necessary
E minSoFar = iterator.next();
while (iterator.hasNext()) {
minSoFar = min(minSoFar, iterator.next());
}
return minSoFar;
}
Returns the least of the specified values according to this ordering. If
there are multiple least values, the first of those is returned.
Params: - iterable – the iterable whose minimum element is to be determined
Throws: - NoSuchElementException – if
iterable
is empty - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the least of the specified values according to this ordering. If
* there are multiple least values, the first of those is returned.
*
* @param iterable the iterable whose minimum element is to be determined
* @throws NoSuchElementException if {@code iterable} is empty
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E min(Iterable<E> iterable) {
return min(iterable.iterator());
}
Returns the lesser of the two values according to this ordering. If the
values compare as 0, the first is returned.
Implementation note: this method is invoked by the default implementations of the other min
overloads, so overriding it will affect their behavior.
Params: - a – value to compare, returned if less than or equal to b.
- b – value to compare.
Throws: - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the lesser of the two values according to this ordering. If the
* values compare as 0, the first is returned.
* <p>
* <p><b>Implementation note:</b> this method is invoked by the default
* implementations of the other {@code min} overloads, so overriding it will
* affect their behavior.
*
* @param a value to compare, returned if less than or equal to b.
* @param b value to compare.
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E min(E a, E b) {
return (compare(a, b) <= 0) ? a : b;
}
Returns the least of the specified values according to this ordering. If
there are multiple least values, the first of those is returned.
Params: - a – value to compare, returned if less than or equal to the rest.
- b – value to compare
- c – value to compare
- rest – values to compare
Throws: - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the least of the specified values according to this ordering. If
* there are multiple least values, the first of those is returned.
*
* @param a value to compare, returned if less than or equal to the rest.
* @param b value to compare
* @param c value to compare
* @param rest values to compare
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E min(
E a, E b, E c, E... rest) {
E minSoFar = min(min(a, b), c);
for (E r : rest) {
minSoFar = min(minSoFar, r);
}
return minSoFar;
}
Returns the greatest of the specified values according to this ordering. If there are multiple greatest values, the first of those is returned. The iterator will be left exhausted: its hasNext()
method will return false
. Params: - iterator – the iterator whose maximum element is to be determined
Throws: - NoSuchElementException – if
iterator
is empty - ClassCastException – if the parameters are not mutually
comparable under this ordering.
Since: 11.0
/**
* Returns the greatest of the specified values according to this ordering. If
* there are multiple greatest values, the first of those is returned. The
* iterator will be left exhausted: its {@code hasNext()} method will return
* {@code false}.
*
* @param iterator the iterator whose maximum element is to be determined
* @throws NoSuchElementException if {@code iterator} is empty
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
* @since 11.0
*/
<E extends T> E max(Iterator<E> iterator) {
// let this throw NoSuchElementException as necessary
E maxSoFar = iterator.next();
while (iterator.hasNext()) {
maxSoFar = max(maxSoFar, iterator.next());
}
return maxSoFar;
}
Returns the greatest of the specified values according to this ordering. If
there are multiple greatest values, the first of those is returned.
Params: - iterable – the iterable whose maximum element is to be determined
Throws: - NoSuchElementException – if
iterable
is empty - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the greatest of the specified values according to this ordering. If
* there are multiple greatest values, the first of those is returned.
*
* @param iterable the iterable whose maximum element is to be determined
* @throws NoSuchElementException if {@code iterable} is empty
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E max(Iterable<E> iterable) {
return max(iterable.iterator());
}
Returns the greater of the two values according to this ordering. If the
values compare as 0, the first is returned.
Implementation note: this method is invoked by the default implementations of the other max
overloads, so overriding it will affect their behavior.
Params: - a – value to compare, returned if greater than or equal to b.
- b – value to compare.
Throws: - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the greater of the two values according to this ordering. If the
* values compare as 0, the first is returned.
* <p>
* <p><b>Implementation note:</b> this method is invoked by the default
* implementations of the other {@code max} overloads, so overriding it will
* affect their behavior.
*
* @param a value to compare, returned if greater than or equal to b.
* @param b value to compare.
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E max(E a, E b) {
return (compare(a, b) >= 0) ? a : b;
}
Returns the greatest of the specified values according to this ordering. If
there are multiple greatest values, the first of those is returned.
Params: - a – value to compare, returned if greater than or equal to the rest.
- b – value to compare
- c – value to compare
- rest – values to compare
Throws: - ClassCastException – if the parameters are not mutually
comparable under this ordering.
/**
* Returns the greatest of the specified values according to this ordering. If
* there are multiple greatest values, the first of those is returned.
*
* @param a value to compare, returned if greater than or equal to the rest.
* @param b value to compare
* @param c value to compare
* @param rest values to compare
* @throws ClassCastException if the parameters are not <i>mutually
* comparable</i> under this ordering.
*/
<E extends T> E max(
E a, E b, E c, E... rest) {
E maxSoFar = max(max(a, b), c);
for (E r : rest) {
maxSoFar = max(maxSoFar, r);
}
return maxSoFar;
}
}