I have an ArrayList of something. I don't now correctly, but I'm pretty sure, that the Object has the compareTo(Object), which returns int in any cases. So, if I want to implement a sort(ArrayList), Objects may by strings, or integers.
private static void sort(ArrayList<String/Integers, or SomethingElse, not sure now> list)
I tried to search something like multi raw type, but I didn't find anything.
How should I do it?
If the List consists of String elements, it will be sorted into alphabetical order. If it consists of Date elements, it will be sorted into chronological order. It will sort any any object/type that contain compareTo() (implements Comparable)
Reference: Collections.sort(list)
If you try to sort a list, the elements of which do not implement Comparable, Collections.sort(list) will throw a ClassCastException
Related
I have 2 lists in java, and I need to validate when there is a match, I set a field of the first list, I tried to do it with streams, but I don't know how to compare the two lists, list don't have same kind of elements I want to do something like this:
public static List<TransactionalityIdDBDTO> getVariationDateRange(List<TransactionalityIdDBDTO> list1,
List<TransactionalityIdDBDTO> list2){
List<TransactionalityIdDBDTO> idDBDTOS= new ArrayList<>();
Iterator prueba=list1.iterator();
while(prueba.hasNext()){
TransactionalityIdDBDTO transactionalityIdDBDTO=(TransactionalityIdDBDTO) prueba.next();
if(transactionalityIdDBDTO.get_id().equals(list2.get_id())){
transactionalityIdDBDTO.setVariation("1232");
idDBDTOS.add(transactionalityIdDBDTO);
}
}
return idDBDTOS;
}
Clase TransactionalityIdDBDTO
public class TransactionalityIdDBDTO extends AbstractDTO {
private TransactionalityDBDTO _id;
private String totalTransaction;
private List<String> idResult;
private String variation;
You can compare lists using equals. e.g
list1.equals(list2);
However,
order is important. If lists contain the same content but in different order they will be considered unequal.
the objects the lists hold must override equals. The criteria for what constitutes two objects of TransactionalityIdDBDTO to be equal are up to you. Based on your code, it seems that id is a good start.
if you plan on using those objects as keys in a map, you must override hashCode too (it's a good idea to do this anyway).
if the lists are not in order but you want to consider them equal, then you should probably sort them first based on the id. You can do that like this.
list1.sort(Comparator.comparing(TransTransactionalityIdDBDTO::get_id));
list2.sort(Comparator.comparing(TransTransactionalityIdDBDTO::get_id));
Objects like String, Integer, and other wrapper classes implement Comparable which means they can be compared to each other of the same type using the above. But instead of get_id which returns a String, say you had get get_Foo. Then the Foo class would need to implement comparable or you would have to provide a more detailed comparator on which to sort.
There are many examples of Comparing objects on the site. I recommend you search them using the [hashCode], [equals], [comparable] and [comparator] tags. Imo, understanding these and how they work are essential for a reasonable working knowledge of Java.
This is a very generalized question, I'll try to be as clear as I can. let's say I have some collection of objects, for simplicity, make them integers. Now I want to make a class which represents these integers as some data structure. In this class I want to implement
a sort function, which sorts the collection according to some defined sorting logic
the iterable interface, where the Iterator traverses in insertion order
How could I make it so that, even if I add integers in unsorted order, e.g.
someCollection.add(1);
someCollection.add(3);
someCollection.add(2);
and then call
Collections.sort(someSortingLogic);
The iterator still traverses in insertion order, after the collection is sorted. Is there a particular data structure I could use for this purpose, or would it be a case of manually tracking which elements are inserted in which order, or something else I can't think of?
Many thanks!
Generally, to solve a problem like this, you maintain two indexes to the values. Perhaps one of those indexes contains the actual values, perhaps both indexes contain the actual values, or perhaps the actual values are stored elsewhere.
Then when you want to walk the sorted order, you use the sorted index to the values, and when you want the insertion order, you use the insert index to the values.
An index can be as simple as an array containing the values. Naturally, you can't store two different values into one spot in an array, so a simple solution is to wrap two arrays in an Object, such that calling the Object's sort() method sorts one array, while leaving the insertion order array untouched.
Fancier data structures leverage fancier techniques, but they all basically boil down to maintaining two orders, the insertion order AND the sort order.
public class SomeCollection {
public void add(int value) {
insertArray = expandIfNeeded(insertArray);
insertArray[insertIndex++] = value;
sortArray = expandIfNeeded(sortArray);
sortArray[sortIndex++] = value;
sort(sortArray);
}
...
}
I'm not sure you've shown us enough code to give you a good answer, but if you have a class that looks a bit like this:
public class Hand implements Iterator<Card>
{
private List<Card> cards = new ArrayList<>();
// Returns iterator for natural ordering of cards
#Override
public Iterator<Card> iterator()
{
return cards.iterator();
}
// Rest of code omitted
Then you can implement a sortedIterator(...) method like this:
// Returns iterator for sorted ordering by Comparator c
public Iterator<Card> sortedIterator(Comparator<? super Card> c)
{
return cards.stream().sorted(c).iterator();
}
If you show us some more code for what you have written, there may be better solutions.
I have a question which appeared in a past paper (I'm revising for my exams) and I came across this word natural order which appears to be a keywords since it was written in bold on the paper. I've looked online at Natural Order but I couldn't find anything that related it to arraylist's like my question asks.
Please note, I do not need help solving the actual question, I just wish to understand what natural order means.
Question:
Write a Java static method called atLeast which takes an ArrayList of objects which
have natural order, an object of the element type of the ArrayList, and an integer n. A
call to the method should return true if at least n elements of the ArrayList are greater
than the element type object according to natural order, otherwise it should return false.
This likely means the objects in the List implement Comparable:
This interface imposes a total ordering on the objects of each class that implements it. This ordering is referred to as the class's natural ordering, and the class's compareTo method is referred to as its natural comparison method.
The declaration would look something like this:
static <T extends Comparable<? super T>>
boolean atLeast(List<T> list, T key, int n) {
...
}
Natural order means the default ordering for a particular type of collection. It actually depends upon the type of collection you are using. eg. if its a string collection, it will be sorted in alphabetical order, for numbers it follows numerical order.
Refer here for better understanding about natural ordering.
You can have a look at here for detail.
For objects to have a natural order they must implement the interface java.lang.Comparable. In other words, the objects must be comparable to determine their order. Here is how the Comparable interface looks:
public interface Comparable<T> {
int compareTo(T o);
}
friends, I am new to Java-Collection. I want to ask does Collections.sort() method only used for/by collections which are List type. I was unable to sort following code:
Collection collection=new HashSet();
collection.add("zebra");
collection.add("frog");
collection.add("bison");
collection.add("puma");
Collections.sort(collection); //error...why??
I know that HashSet is used for unique elements. But is there any way to sort this collection?
Collections.sort method expects a collection that implements a List<T> interface. This makes sense, because lists have a defined sequence. In other words, your program has complete control of the order of what goes in the list.
Unlike lists, sets are either unordered, or specify their own, specific ordering. That is why trying to sort a Set does not make sense: it is the set, not your program, that defines the ordering of the items in the set collection. Your program can provide the logic to customize that ordering, but you cannot take an existing set, and force a different order on its items from the outside.
If you would like to get all items of a set collection in a sorted order, copy your set into an array list, and sort the results.
The error is because the Collections class only supports a List.
public static <T extends Comparable<? super T>> void sort(List<T> list)
To sort your collection, you can try something like:
Collection collection=new HashSet();
collection.add("zebra");
collection.add("frog");
collection.add("bison");
collection.add("puma");
ArrayList<String> temp = new ArrayList<String>(collection);
Collections.sort(temp);
collection = new HashSet(temp);
Hope this helps.
Yes, the Collections.sort methods are only for lists.
You can't sort HashSet, but a TreeSet is automatically sorted as you add items, and LinkedHashSet is sorted by insertion order.
No. There is by definition no way to sort a HashSet. You can use a TreeSetinstead tho'.
My first step with these questions is to look at Java's documentation, which will help you a lot in understanding and debugging things.
http://docs.oracle.com/javase/7/docs/api/java/util/Collections.html
If you look at the sort method, there, it is expecting a List.
sort(List<T> list)
It has another overriden version, but this also needs a list, as well as a comparator.
sort(List<T> list, Comparator<? super T> c)
This is why you are getting an error. There is not a method defined for sort (HashSet)
sort(List<T> list) of Collections is the original method which expects of type List. But To sort Set basically we use TreeSet, which sorts elements by the help of compare() or compareTo() methods of Comparator and Comparable interfaces respectively.
Java collections has different semantics.
List is a set of objects that may include equals or even same elements with the order defined;
Set is a set of objects that doesn't include equal and same elements and doesn't specify the order;
SortedSet is the same as set except for it defines element order - they are stored in the order determined by compareTo() or comparator;
Thus, the only type of collection for which sorting makes sense is List.
List<MyClass> myclassList = (List<MyClass>) rs.get();
TreeSet<MyClass> myclassSet = new TreeSet<MyClass>(myclassList);
I don't understand why this code generates this:
java.lang.ClassCastException: MyClass cannot be cast to java.lang.Comparable
MyClass does not implement Comparable. I just want to use a Set to filter the unique elements of the List since my List contains unncessary duplicates.
Does MyClass implements Comparable<MyClass> or anything like that?
If not, then that's why.
For TreeSet, you either have to make the elements Comparable, or provide a Comparator. Otherwise TreeSet can't function since it wouldn't know how to order the elements.
Remember, TreeMap implements SortedSet, so it has to know how to order
the elements one way or another.
You should familiarize yourself with how implementing Comparable
defines natural ordering for objects of a given type.
The interface defines one method, compareTo, that must return a negative integer, zero, or a positive integer if this object is less than, equal to, or greater than the other object respectively.
The contract requires that:
sgn(x.compareTo(y)) == -sgn(y.compareTo(x))
it's transitive: x.compareTo(y)>0 && y.compareTo(z)>0 implies x.compareTo(z)>0
x.compareTo(y)==0 implies that sgn(x.compareTo(z)) == sgn(y.compareTo(z)) for all z
Additionally, it recommends that:
(x.compareTo(y)==0) == (x.equals(y)), i.e. "consistent with equals
This may seem like much to digest at first, but really it's quite natural with
how one defines total ordering.
If your objects can not be ordered one way or another, then a TreeSet wouldn't make sense. You may want to use a HashSet instead, which have its own contracts. You are likely to be required to #Override hashCode() and equals(Object) as appropriate for your type (see: Overriding equals and hashCode in Java)
If you don't pass an explicit Comparator to a TreeSet, it will try to compare the objects (by assuming they are Comparable). And if they aren't Comparable, it cannot compare them, so this exception is thrown!
TreeSets are sorted sets and require either objects to be Comparable or a Comparator to be passed in to determine how to sort the objects in the Set.
If you just want the set to remove duplicates, used a HashSet, although that will shuffle the order of the objects returned by the Iterator in ways that appear random.
But if you want to preserve the order somewhat, use LinkedHashSet, that will at least preserve the insertion order of the list.
TreeSet is only appropriate if you need the Set sorted, either by the Object's implementation of Comparable or by a custom Comparator passed to the TreeSet's constructor.