com.google.common.collect.SortedIterables Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of guava Show documentation
Show all versions of guava Show documentation
Guava is a suite of core and expanded libraries that include
utility classes, google's collections, io classes, and much
much more.
/*
* Copyright (C) 2011 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 com.google.common.collect;
import static com.google.common.base.Preconditions.checkNotNull;
import com.google.common.annotations.GwtCompatible;
import com.google.common.base.Function;
import com.google.common.collect.Multiset.Entry;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.SortedSet;
/**
* Utilities for dealing with sorted collections of all types.
*
* @author Louis Wasserman
*/
@GwtCompatible
final class SortedIterables {
private SortedIterables() {}
/**
* Returns {@code true} if {@code elements} is a sorted collection using an ordering equivalent
* to {@code comparator}.
*/
public static boolean hasSameComparator(Comparator comparator, Iterable elements) {
checkNotNull(comparator);
checkNotNull(elements);
Comparator comparator2;
if (elements instanceof SortedSet) {
SortedSet sortedSet = (SortedSet) elements;
comparator2 = sortedSet.comparator();
if (comparator2 == null) {
comparator2 = (Comparator) Ordering.natural();
}
} else if (elements instanceof SortedIterable) {
comparator2 = ((SortedIterable) elements).comparator();
} else {
comparator2 = null;
}
return comparator.equals(comparator2);
}
/**
* Returns a sorted collection of the unique elements according to the specified comparator. Does
* not check for null.
*/
@SuppressWarnings("unchecked")
public static Collection sortedUnique(
Comparator comparator, Iterator elements) {
SortedSet sortedSet = Sets.newTreeSet(comparator);
Iterators.addAll(sortedSet, elements);
return sortedSet;
}
/**
* Returns a sorted collection of the unique elements according to the specified comparator. Does
* not check for null.
*/
@SuppressWarnings("unchecked")
public static Collection sortedUnique(
Comparator comparator, Iterable elements) {
if (elements instanceof Multiset) {
elements = ((Multiset) elements).elementSet();
}
if (elements instanceof Set) {
if (hasSameComparator(comparator, elements)) {
return (Set) elements;
}
List list = Lists.newArrayList(elements);
Collections.sort(list, comparator);
return list;
}
E[] array = (E[]) Iterables.toArray(elements);
if (!hasSameComparator(comparator, elements)) {
Arrays.sort(array, comparator);
}
return uniquifySortedArray(comparator, array);
}
private static Collection uniquifySortedArray(
Comparator comparator, E[] array) {
if (array.length == 0) {
return Collections.emptySet();
}
int length = 1;
for (int i = 1; i < array.length; i++) {
int cmp = comparator.compare(array[i], array[length - 1]);
if (cmp != 0) {
array[length++] = array[i];
}
}
if (length < array.length) {
array = ObjectArrays.arraysCopyOf(array, length);
}
return Arrays.asList(array);
}
/**
* Returns a collection of multiset entries representing the counts of the distinct elements, in
* sorted order. Does not check for null.
*/
public static Collection> sortedCounts(
Comparator comparator, Iterator elements) {
TreeMultiset multiset = TreeMultiset.create(comparator);
Iterators.addAll(multiset, elements);
return multiset.entrySet();
}
/**
* Returns a collection of multiset entries representing the counts of the distinct elements, in
* sorted order. Does not check for null.
*/
public static Collection> sortedCounts(
Comparator comparator, Iterable elements) {
if (elements instanceof Multiset) {
Multiset multiset = (Multiset) elements;
if (hasSameComparator(comparator, elements)) {
return multiset.entrySet();
}
List> entries = Lists.newArrayList(multiset.entrySet());
Collections.sort(
entries, Ordering.from(comparator).onResultOf(new Function, E>() {
@Override
public E apply(Entry entry) {
return entry.getElement();
}
}));
return entries;
} else if (elements instanceof Set) { // known distinct
Collection sortedElements;
if (hasSameComparator(comparator, elements)) {
sortedElements = (Collection) elements;
} else {
List list = Lists.newArrayList(elements);
Collections.sort(list, comparator);
sortedElements = list;
}
return singletonEntries(sortedElements);
} else if (hasSameComparator(comparator, elements)) {
E current = null;
int currentCount = 0;
List> sortedEntries = Lists.newArrayList();
for (E e : elements) {
if (currentCount > 0) {
if (comparator.compare(current, e) == 0) {
currentCount++;
} else {
sortedEntries.add(Multisets.immutableEntry(current, currentCount));
current = e;
currentCount = 1;
}
} else {
current = e;
currentCount = 1;
}
}
if (currentCount > 0) {
sortedEntries.add(Multisets.immutableEntry(current, currentCount));
}
return sortedEntries;
}
TreeMultiset multiset = TreeMultiset.create(comparator);
Iterables.addAll(multiset, elements);
return multiset.entrySet();
}
static Collection> singletonEntries(Collection set) {
return Collections2.transform(set, new Function>() {
@Override
public Entry apply(E elem) {
return Multisets.immutableEntry(elem, 1);
}
});
}
}