3

I'm facing a problem when operating on an ArrayList of ArrayList in Java. I have this thing in my code-

ArrayList<ArrayList<Integer>> L1 = new ArrayList<ArrayList<Integer>>();

Problem is, I have no idea as to how I should operate on this (addition, removal, traversal etc.). I wish to create an adjacency list (for implementing simple, undirected graphs), and my instructor suggests that I should create an ArrayList of ArrayList. I know I can do the following to add new element-

L1.add(//Something I want to add);

But this throws up an error in the current case for obvious reasons.

6 Answers 6

2

An ArrayList of an ArrayList, just think that the outer object is an ArrayList and you are done.

ArrayList<ArrayList<Integer>> list2d = new ArrayList<ArrayList<Integer>>();
// add an element to the list
list2d.add(new ArrayList<Integer>());
// retrieve a list 
ArrayList<Integer> list1d = list2d.get(0);
// add an integer
list2d.get(0).add(123);

By the way, an adjacency list is just a list of edges, there's no need to store them for each vertex, especially if the graph is undirected. A list of Edge would be enough:

class Edge {
  Vertex v1, v2;
}

ArrayList<Edge> adjacencyList;

If you want to store them on a per vertex basis then you could avoid using a list of lists by encapsulating the edges inside the vertex class itself but this will require twice the edges:

class Vertex {
  int value;
  ArrayList<Vertex> adjacency;
}

but which one is best depends on what kind of operation you need to perform on the graph. For a small graph there is no practical difference.

Another possible implementation, if you just need to know if two vertex are connected:

class Edge {
  public final int v1, v2;

  public boolean equals(Object o) { return o != null && o instanceof Edge && o.hashCode() == hashCode(); }

  public int hashCode() { return v1 ^ v2; } // simple hash code, could be more sophisticated
}

Set<Edge> adjacencyList = new HashSet<Edge>();
Sign up to request clarification or add additional context in comments.

4 Comments

This might be misleading. By adjacencyList, it might be also meant a list of neighbour vertices (their indices) of certain vertex, thus L1.get(i) will return list of all vertex indices neighboring with index with idx i.
The advancement of per vertex lists of edges is getting all neigbours n of the vertex v in O(n(v)) time where n(v) is the number of neighbours of v. If only edges are stored, it will require O(e) time where e is the number of edges in the graph. The difference could be critical in some applications.
@kenor: in a context in which such a difference would be critical you won't be using an ArrayList at all, you would use sets for adjacency lists inside vertices in any case. There's no need to have an O(n) lookup when you can have O(1) if performance is critical.
of course, that was more of a hypothetical note, since the asker was for some reason instructed to use list of lists
1

Try L1.get(i).add(whatever);, and of course first check whether L1.get(i) exists, otherwise add that inner list first.

It's something like this:

List<List<Integer>> L1 = new ArrayList<List<Integer>>(); //better use interfaces

List<Integer> first = null;
if( L1.size() > 0) {
 first = L1.get(0); //first element
}
else {
  first = new ArrayList<Integer>();
  L1.add(first);      
}

first.add(4711); //or whatever you like to add

Comments

1
List<List<Integer>> L1 = new ArrayList<ArrayList<Integer>>();    
List<Integer> list1 = new ArrayList<Integer>();     
list1.add(1);
list1.add(2);
list1.add(3);
list1.add(4);
list1.add(5);

//add list to the list

L1.add(list1); 

iterate over the list of lists

for( List<Integer> list: L1 ){
      for(Integer i:list){
          System.out.println(i);
      }
}

1 Comment

L1.add(list1); would not work unless L1 is defined to be List<List<Integer>>.
1

You can only add objects of type ArrayList to L1. So you could do this:

ArrayList<ArrayList<Integer>> firstList = new ArrayList<ArrayList<Integer>>();

ArrayList<Integer> secondList = new ArrayList<Integer>();
secondList.add(0);

firstList.add(secondList);

Comments

1
L1.add(new ArrayList<Integer>());

will create a new List within the first list. Then you can

L1.get(0).add(5)

1 Comment

Yep, sorry, no IDE :X
1

To add a new element to the outer array:

ArrayList<Integer> inner = new ArrayList<Integer>();
L1.add(inner);

Then to add element to the inner array:

   int exampleInt = 10;
   ArrayList<Integer> inner = L1.get(0);
   inner.add(exampleInt);

To traverse all elements in all arrays:

   for (ArrayList<Integer> inner : L1)
   {
      for (Integer element : inner)
      {
         System.out.println(element);
      }
   }

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.