How do I create a generic array list in Java that could accept both integers and array?
[123,[],112,[],10]
How do I create a generic array list in Java that could accept both integers and array?
[123,[],112,[],10]
Both int (Integer wrapper) and array's common base class is Object. So create ArrayList using Object type.
ArrayList<Object> list= new ArrayList<Object>();
But this is not the right way to solve this problem and there is no use of Generics here to make run-time safety. So, re-design your program and allocate each type in seperate list or use any other appropriate Collection type.
Well, the fastest way might be create an auxiliar object that is composed by boths Integers and array letting you to use boths by equal
Use a class which has an int
and an array as its instance variables. Then create an ArrayList
like
import java.util.ArrayList;
public class Hello {
public static void main(String[]args) {
ArrayList<Intarray> myArrayList = new ArrayList<Intarray>();
int[] arr = {3,4,5};
myArrayList.add(new Intarray(2,arr));
}
}
class Intarray {
private int numbers;
private int[] myArray;
public Intarray(int numbers, int[] myArray){
this.numbers = numbers;
this.myArray = myArray;
}
}
Create the array list at the Generalization level for all the objects you need in the List. In this case,i.e for int and array, it is java.lang.Object.
Here's a small test I ran:
public static void main(String[] args) {
List<Object> both = new ArrayList<Object>();
both.add(1);
both.add(args);
System.out.println(both);
}
Produces: [1, [Ljava.lang.String;@1db9742]
As @AbtPst suggested, the most suitable solution would be to have a list of lists. This can be done in many different ways. Personally, I'd create a class with two constructors.
class NumericElement
{
private ArrayList<int> elements;
public NumericElement(int newElement)
{
elements = new ArrayList<int>();
elements.add(newElement);
}
public NumericElement(ArrayList<int> newElements)
{
elements = new ArrayList<int>(newElements); // copying array elements to the new array.
}
public ArrayList<int> getElements()
{
return elements;
}
}
You can define a List
class with a type-safe interface, hiding an unsafe List<Object>
as an internal implementation detail.
This is more work than just using a List<Object>
directly. If your list is used only by one class, just use a List<Object>
, as an implementation detail of that one class. But if your list is exposed to access by more than just one class, consider using this type-safe approach.
First, define an interface that can represent either an int or a array of ints.
public interface IScalarOrArrayInt { }
And define a sub-interface for each possible element type:
public interface IScalarInt extends IScalarOrArrayInt {
public int getScalarInt();
}
public interface IArrayInt extends IScalarOrArrayInt {
public int[] getIntArray();
}
Then define your list class and its representation. It's interface can be a List<IScalarOrArrayInt>
. The representation can be a List<Object>
, so that you can put Integer and int[] objects into it directly, without wrapper objects.
public class ListOfScalarsAndArray extends AbstractList<IScalarOrArrayInt> {
private static List<Object> m_list = new ArrayList<Object>();
As noted in the AbstractList
documentation, you'll want to define several methods to allow modifying your list. You can delegate them to the internal list, but wrap the return values.
@Override
public void add(int index, IScalarOrArrayInt element) {
m_list.add( index, element );
}
@Override
public IScalarOrArrayInt remove(int index) {
return wrap( m_list.remove( index ));
}
@Override
public IScalarOrArrayInt set(int index, IScalarOrArrayInt element) {
return wrap( m_list.set( index, element ));
}
For the convenience of callers, you can add some methods that accept an unwrapped int
or int[]
. For example:
public void add( int element ) {
m_list.add( element );
}
public void add( int[] element ) {
m_list.add( element );
}
To satisfy the standard List<> interface, you can wrap return values. Your class controls the internal list, so it alone controls the possible types of list members.
private IScalarOrArrayInt wrap( Object o ) {
if ( o instanceof Integer ) {
final int i = (Integer) o;
return new IScalarInt() {
@Override
public int getScalarInt() {
return i;
}
};
}
else {
assert( o instanceof int[] );
final int[] a = (int[]) o;
return new IArrayInt() {
@Override
public int[] getIntArray() {
return a;
}
};
}
}