ArrayList<int[]> containing a value - java

if i have an ArrayList<int[]> example and I want to check if {2,4} is in it how would I do this?
exaple.contains({2,4}); //doesn't work
and
exaple.contains(2,4); //doesn't work either
what is wrong with the code?

Arrays don't override the Object.equals() method (that ArrayList.contains() uses to compare objects). So an array is only equal to itself. You'll have to loop through the list and compare each element with your array using Arrays.equals().
What I suspect, though, is that you shouldn't have a List<int[]>, but a List<Coordinate>. The Coordinate class could then override equals() and hashCode(), and you would be able to use
example.contains(new Coordinate(2, 4))
You could also use a List<List<Integer>>, but if what I suspect is true (i.e. you're using arrays to hold two coordinates that should be in class), then go with the custom Coordinate class.

Even if you did it properly, ie:
int[] vals = {2, 4};
exaple.contains(vals);
You would not return true, because the contains method will use the equals method. Unless you have overridden the equals method, then this will always resolve to false, unless you pass in the exact same array.

You might want to take a look at this. And please post a bit of you're code.
i need to find a integer data in arraylist?

The contains() method checks, if ArrayList contains a specific object, it doesn't concern itself with the values inside an object. In other words, if you instantiate two {2,4} arrays, it will be two different objects and contains() method will diferentiate between them.
What you need to do is either override the contains() method to look on the content of arrays, instead of only the reference, or you can drop the contains() method completely and check it by hand.

Related

Easily Change the .contains() method in the Collections interface in Java for Asserting Equality

I'm wondering if there is a way to easily modify the ".contains()" method in the List interface in Java without creating a custom class. For example:
When dealing with a collection of arrays in java, the .contains() method will always return false because the .contains() method always checks for equality with a generic .equals() call from the Object class that only returns true if the compared objects have the same reference in memory. However, with arrays, it is much more useful to do an Arrays.equals() check on the two arrays.
Code:
public class Temp {
public static void main(String[] args) {
int[] myIntArray = new int[] {1, 2, 3};
List<int[]> myList = new ArrayList<>();
myList.add(myIntArray);
System.out.println(myList.contains(new int[] {1, 2, 3}));
} // Output in the console: false
// Preferred output: true
}
I understand that it is possible to do this rather easily by using a for loop and iterating over the whole list using the Arrays.equals() method, but the goal for me is to learn how to easily sculpt the .contains() method into what I need for future use. Thanks a lot!
No. contains() can't do anything other than use Object.equals, because that's required by the specification.
That's not to say that it's not reasonable to want a notion of contains for an array; merely that you can't overload the existing concept.
You can straightforwardly create a static method:
static <T> boolean containsArray(List<? extends T[]> list, T[] query) {
return list.stream().anyMatch(e -> Arrays.equals(e, query));
}
And then invoke this where you would otherwise invoke list.contains(query).
This has the advantage that it works for any list (with reference-typed array elements): you don't have to create it specially, merely update these specialized comparisons.
(The above would work for any reference-typed array. You'd need to specialize it for primitive-typed arrays).
It also has the advantage that you don't have to deal with the thorny consequences highlighted by Stephen C (e.g. how indexOf, remove etc work).
There's another alternative: use a list element type which supports equals "correctly". For example, you can wrap arrays using Arrays.asList to store them in the list, so you have a List<List<T>> instead of List<T[]>.
This would be quite an invasive change: it would require changing the type of the list throughout your code; you've not provided any indication of how pervasively-used your list of arrays is.
I am wondering if there is a way to easily modify the contains method in the List interface in Java without creating a custom class.
There isn't a way. The contains method of the standard implementations of List behave as specified by the List API; i.e. they use the equals method.
The flip-side that it would not be hard to extend the ArrayList class and override contains to do what you want. But if you are doing it properly, you need to consider whether you want:
indexOf and lastIndexOf to be consistent with contains
the semantics of equals(Object) to be consistent with it
the semantics of a list returned by sublist(int, int) to be consistent with the semantics of the main list.

At which point array class is being created in java?

Today I tried to compare two arrays using equals(), it obviously failed, I started diggin' etc etc, and after some research I can't quite figure out: at which point in time the class for an array is being created? Cuz I know that int [] a leads to creation of an array class for integers. Who creates it? Why it was impossible to override Object.equals() so that it doesn't compare two objects and compares elements of arrays instead? Would be very grateful if someone could explain or provide a link, which would help to understand that.
Array doesn't override equals() of the Object class.
So it will not use the equals() method of the objects that it holds when equals() is invoked on an Array.
If you want to compare two arrays of integer, you can use Arrays.equals() method.
If it doesn't suit you, create your own method to compare two array of integers.
But overriding equals() of Array is not possible as the class is final and besides it seems rather a weird approach.

Most optimised way to merge two List(s) of objects without using Comparator

How, do you think, can we merge two List implementations, say ArrayList(s), without having to implement the object type as Comparable, or overriding .equals() method anyways. Basically, no change to that class is allowed.
Now, the object has 4 attributes - code, name, (boolean), (float). Name cannot be used as the basis of comparison, and it is not necessary that code will always be a non-null value. Basically, either code is not null, or the boolean is set to true.
Now, if the two elements in the list are conflicting, then their (float) values need to be added up.
How can we perform this merge in most optimized way?
Its not that we can't use name as the unique identifier for each object, but issue is the names are too long which means string comparison will also be costly !
If you cannot change the class to implement Comparable, you can still use external Comparator objects.

Java HashSet 2d array duplicate recognition

I need to check whether a list/set of 2d char arrays contains an exact duplicate of another 2d char array that I pass as a parameter. My idea was to make a HashSet and then use the contains() method, but that's not really working; I assume it has to do with me passing the method 2D arrays. If possible, I don't want iterate through every item in the list because that is too costly. Please help me out here. Thanks!
That would never work because the hashCode of the arrays is based on the Object's so unless you are trying to find same references, you will never get a contains to evaluate to true.
You should create a wrapper for your arrays and override the hashCode and equals. You can use Arrays.deepEquals for this purpose

Is there an easy way to remove the same object from 2 linked lists?

I have 2 linked lists.
I have the same object in both of those lists. By same object, I mean the object has the same state, but is referenced by a different object pointer.
I can call .remove(object); from the first list to remove it, but if I do the same for the second list it is not removed (because the object pointer reference is different)
Is there an easy way to remove objects with the same state from various lists?
Thinking about it, I will probably loop through the second list comparing state on its objects, but I was looking for a cleaner way
Override the equals method for the object. If they have similar equivalence functionality they should be removed correctly from both lists.
Edit - for the sake of correctnes:
You should always override the hashCode method when overriding the equals method. Failure to do so may not show any strange functionality in your List but once you try to use the same object in say a HashMap, you may find that the remove or put may not function like you wanted.
If the objects have the same state, then it is probably correct for you to override their equals and hashCode methods to reflect this. If the objects are the same as far as the equals method is concerned, then you can call remove on both lists.
If the linked lists are implemented properly, the fact that different objects are being pointed to in memory should not prevent this from working. According to the List API, the remove method:
...removes the element with the lowest index i such that (o==null ? get(i)==null : o.equals(get(i))) (if such an element exists)...
You must override both equals() and hashCode() on you object. When these are not overriden the default behaviour is to compare object identity ie the reference. When you override Equals you can change the comparison to be based on the object state, ie logically equality. It is important to remember to override hashCode as well, as if this is not done it can lead to strange behaviour when you object is used in a HashSet or HashTable.

Categories

Resources