blob: dc3e51c57e12522a6ec4b8b2cffaa98eb4973017 [file] [log] [blame]
/**
* Copyright (c) 2011-2012 Eclipse contributors and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v2.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v20.html
*/
package org.eclipse.emf.ecore.xcore.lib;
import java.util.Collection;
import java.util.Comparator;
import org.eclipse.emf.common.util.BasicEList;
import org.eclipse.emf.common.util.ECollections;
import org.eclipse.emf.common.util.EList;
import org.eclipse.xtext.xbase.lib.Functions;
import org.eclipse.xtext.xbase.lib.Inline;
import org.eclipse.xtext.xbase.lib.ListExtensions;
import org.eclipse.xtext.xbase.lib.Pure;
import org.eclipse.xtext.xbase.lib.Functions.Function1;
import com.google.common.collect.Lists;
/**
* An extension library for {@link EList ELists}.
*/
public class XcoreEListExtensions
{
/**
* Returns an unmodifiable view of the specified list.
* @param list the list for which an unmodifiable view is to be returned. May not be <code>null</code>.
* @return an unmodifiable view of the specified list.
*/
@Inline(value="$2.$3unmodifiableEList($1)", imported=ECollections.class)
public static <T> EList<T> unmodifiableView(EList<? extends T> list)
{
return ECollections.unmodifiableEList(list);
}
/**
* Returns an immutable copy of the specified list.
*
* @param list the list for which an immutable copy should be created. May not be <code>null</code>.
* @return an immutable copy of the specified list.
*/
public static <T> EList<T> immutableCopy(EList<? extends T> list)
{
final Object[] elements = list.toArray();
return
new UnmodiableArrayView<T>(elements);
}
/**
* Sorts the specified list itself into ascending order according to the natural ordering of its elements.
*
* @param list the list to be sorted. May not be <code>null</code>.
* @return the sorted list itself.
*/
public static <T extends Comparable<? super T>> EList<T> sortInplace(EList<T> list)
{
ECollections.sort(list);
return list;
}
/**
* Sorts the specified list itself into ascending according to the order induced by the specified comparator.
*
* @param list the list to be sorted. May not be <code>null</code>.
* @param comparator the comparator to be used; it may be <code>null</code> to indicate that the natural ordering of the elements should be used.
* @return the sorted list itself.
*/
public static <T> EList<T> sortInplace(EList<T> list, Comparator<? super T> comparator)
{
ECollections.sort(list, comparator);
return list;
}
/**
* Sorts the specified list in ascending order according to the nature order of the corresponding element induced by the key function.
*
* @param list the list to be sorted. May not be <code>null</code>.
* @param key the key function to induce comparison keys. May not be <code>null</code>.
* @return the sorted list itself.
*/
public static <T, C extends Comparable<? super C>> EList<T> sortInplaceBy(EList<T> list, final Functions.Function1<? super T, C> key)
{
Comparator<T> comparator =
new Comparator<T>()
{
public int compare(T o1, T o2)
{
C left = key.apply(o1);
C right = key.apply(o2);
return left.compareTo(right);
}
};
ECollections.sort(list, comparator);
return list;
}
/**
* Provides a reverse view of the given list which is especially useful for traversing a list backwards in a for-each loop.
*
* @param list the list whose elements should be viewed in reverse. May not be <code>null</code>.
* @return a list with the same elements as the given list, in reverse order.
*/
@Pure
public static <T> EList<T> reverseView(EList<T> list)
{
return ECollections.asEList(Lists.reverse(list));
}
/**
* Reverses the order of the elements in the specified list.
* The list itself will be modified.
*
* @param list the list whose elements are to be reversed.
* @return the list itself.
* @throws UnsupportedOperationException if the specified list does not support {@link EList#move(int, int) move}.
*/
public static <T> EList<T> reverse(EList<T> list)
{
ECollections.reverse(list);
return list;
}
/**
* Returns a transformed view of the given list.
* Additions are not supported but all other changes to view are reflected in the underlying list and all changes to the underlying list are reflected in the view.
* The mapping is done lazily, i.e., each list access applies the transformation.
*
* @param list the list to map. May not be <code>null</code>.
* @param transformation the transformation to induce the mapping. May not be <code>null</code>.
* @return a list that effectively contains the result of the transformation.
*/
@Pure
public static <T, R> EList<R> map(EList<T> list, Function1<? super T, ? extends R> transformation)
{
return ECollections.asEList(ListExtensions.map(list, transformation));
}
static class UnmodiableArrayView<T> extends BasicEList<T>
{
private static final long serialVersionUID = 1L;
UnmodiableArrayView(Object[] data)
{
super(data.length, data);
}
@Override
public void setData(int size, Object[] data)
{
throw new UnsupportedOperationException();
}
@Override
public void grow(int minimumCapacity)
{
throw new UnsupportedOperationException();
}
@Override
public void shrink()
{
throw new UnsupportedOperationException();
}
@Override
public T setUnique(int index, T object)
{
throw new UnsupportedOperationException();
}
@Override
public T remove(int index)
{
throw new UnsupportedOperationException();
}
@Override
public boolean remove(Object object)
{
throw new UnsupportedOperationException();
}
@Override
public boolean removeAll(Collection<?> collection)
{
throw new UnsupportedOperationException();
}
@Override
public void clear()
{
throw new UnsupportedOperationException();
}
}
}