/*******************************************************************************
* Copyright (c) 2007, 2010 Association for Decentralized Information Management
* in Industry THTH ry.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* VTT Technical Research Centre of Finland - initial API and implementation
*******************************************************************************/
package org.simantics.utils.datastructures.collections;
import gnu.trove.map.hash.TObjectIntHashMap;
import gnu.trove.set.hash.THashSet;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.simantics.utils.datastructures.Pair;
/**
* @author Tuukka Lehtonen
*/
public final class CollectionUtils {
/**
* Add the elements in toBeAdded
to addTo. The only difference
* to {@link Collection#addAll(Collection)} is that toBeAdded
* may be null.
*
* @param
* @param toBeAdded collection of elements to be added to addTo
or
* null
to do nothing
* @param addTo the collection the elements should be added to
* @return true
if the destination collection changed as a
* result of the operation
*/
public static boolean checkedAdd(Collection toBeAdded, Collection addTo) {
assert addTo != null;
if (toBeAdded == null)
return false;
return addTo.addAll(toBeAdded);
}
/**
* @return the accumulated size of all the specified collections
*/
public static int sizeAll(Collection>... collections) {
int size = 0;
for (Collection> c : collections)
size += c.size();
return size;
}
/**
* @return a new ArrayList that sequentially contains all the elements in
* the specified collections
*/
public static Collection join(@SuppressWarnings("unchecked") Collection... collections) {
int size = sizeAll(collections);
ArrayList result = new ArrayList(size);
for (Collection c : collections)
result.addAll(c);
return result;
}
/**
* @return a new HashSet that contains once all the elements in the
* specified collections
*/
public static Set join(@SuppressWarnings("unchecked") Set... collections) {
int size = sizeAll(collections);
HashSet result = new HashSet(size);
for (Collection c : collections)
result.addAll(c);
return result;
}
/**
* A specialization of {@link #join(Collection...)} for two arguments.
*/
public static Collection join(Collection first, Collection second) {
int size = first.size();
size += second.size();
ArrayList result = new ArrayList(size);
result.addAll(first);
result.addAll(second);
return result;
}
static class PairFirstComparator> implements Comparator> {
@Override
public int compare(Pair o1, Pair o2) {
return o1.first.compareTo(o2.first);
}
}
static class PairSecondComparator> implements Comparator> {
@Override
public int compare(Pair, V> o1, Pair, V> o2) {
return o1.second.compareTo(o2.second);
}
}
public static Collection> valueSortedEntries(TObjectIntHashMap map) {
ArrayList> result = new ArrayList>();
for(K key : map.keySet()) result.add(new Pair(key, map.get(key)));
Collections.sort(result, new PairSecondComparator());
return result;
}
public static > List> valueSortedEntries(Map map) {
ArrayList> result = new ArrayList>();
for(Map.Entry entry : map.entrySet()) result.add(new Pair(entry.getKey(), entry.getValue()));
Collections.sort(result, new PairSecondComparator());
return result;
}
public static , V> List sortedBy(List keys, List values) {
ArrayList> work = new ArrayList>();
for(int i=0;i());
ArrayList result = new ArrayList();
for(Pair pair : work) result.add(pair.first);
return result;
}
public static ,V> Collection sortByFirst(List> collection) {
Collections.sort(collection, new PairFirstComparator());
ArrayList values = new ArrayList();
for(Pair pair : collection) values.add(pair.second);
return values;
}
/**
* A specialization of {@link #join(Set...)} for two arguments.
*/
public static Set join(Set first, Set second) {
int size = first.size();
size += second.size();
HashSet result = new HashSet(size);
result.addAll(first);
result.addAll(second);
return result;
}
/*
* Some tests.
*/
@SuppressWarnings({ "unused", "unchecked" })
public static void main(String[] args) {
Collection c1 = Collections.singleton("FOO");
Collection c2 = Collections.singleton("BAR");
Collection c3 = Collections.singleton("BAZ");
Collection c4 = Collections.singleton("FOO");
Collection c123 = join(c1, c2, c3);
Collection c12 = join(c1, c2);
Set s1 = Collections.singleton("FOO");
Set s2 = Collections.singleton("BAR");
Set s3 = Collections.singleton("BAZ");
Set s4 = Collections.singleton("FOO");
Set s123 = join(s1, s2, s3);
Set s12 = join(s1, s2);
Set s14 = join(s1, s4);
}
public static void toggle(Set src, Set toggleSet)
{
for (T i : toggleSet)
{
if (src.contains(i))
src.remove(i);
else
src.add(i);
}
}
public static List toList(@SuppressWarnings("unchecked") T...objs)
{
ArrayList result = new ArrayList(objs.length);
for (T o : objs)
result.add(o);
return result;
}
public static Set toSet(@SuppressWarnings("unchecked") T...objs)
{
THashSet result = new THashSet(objs.length);
for (T o : objs)
result.add(o);
result.compact();
return result;
}
/**
* Remove elements that appear more than once. Keep order otherwise.
* @param list to be pruned
*/
public static void unique(List> list) {
int c = list.size();
int i = c-1;
while (i>0) {
Object o = list.get(i);
int index = list.indexOf(o);
if (index>=0) {
list.remove(index);
c--;
i--;
} else {
i--;
}
}
}
public static T element(Collection collection, int n) {
if (collection instanceof List>)
return ((List) collection).get(n);
if(n >= collection.size()) throw new IllegalArgumentException();
Iterator it = collection.iterator();
for( int i=0;i collection, String separator) {
StringBuilder sb = new StringBuilder();
int index = 0;
for (Object o : collection) {
if ( index++>0 ) sb.append(separator);
sb.append( o.toString() );
}
return sb.toString();
}
public static String toString(Object[] array, String separator) {
StringBuilder sb = new StringBuilder();
int index = 0;
for (Object o : array) {
if ( index++>0 ) sb.append(separator);
sb.append( o.toString() );
}
return sb.toString();
}
}