This material was first published by Code Explosion | Code that explodes convention
Java collection framework is very common to every java programmer, again for the beginner, I’m going to share my ideas about it. It’s really helpful to manage object easily. Java collection framework is more likely array, but difference is, Collections can dynamically change their size. Today I’m going to write only about the List.
List:
The java.util.List interface is a subtype of the java.util.Collection interface. It represents an order list of objects. User can access the elements of list in a specific order or by and integer index. List allows to insert duplicate elements. Interestingly you can insert null object even in a list.
As it is an interface, there of course it has implementation. ArrayList, LinkedList, Vector, Stack are the implementation of List. All List types support basic operation like adding object, removing objects, accessing objects and iterating through the List.
There are also List implementation in java.util.concurrent package. Concurrency is the part of parallel programming, immutability, threads, executor frameworks etc. We better discuss this part later.
How to create list instance:
Creating list instance is too easy.
package org.codexplo.blog.list; import java.util.ArrayList; import java.util.LinkedList; import java.util.List; import java.util.Stack; import java.util.Vector; public class ListInstance { public static void main(String[] args) { List listA = new ArrayList(); List listB = new LinkedList(); List listC = new Vector(); List listD = new Stack(); } }
Adding and accessing Elements
To add element, you need to call its add() methods. This method is inherited from java.util.Collection interface.
There are two overload method in list.
boolean add(E e); void add(int index, E element);
The first one add elements t0 the end of the list and return true if the list is changed as a result of the call otherwise false.
and the second one add element at the specified position in the list. If any element is already in that position, it shifts the elements concurrently to the next.
package org.codexplo.blog.list; import java.util.ArrayList; import java.util.List; public class AddingAndAccessingList { public static void main(String[] args) { List list = new ArrayList(); list.add("a"); list.add("b"); list.add("c"); list.add(0, "abcd"); System.out.println(list.get(0)); System.out.println(list.get(1)); } }
The first three add() calls add a string instance to the end of the list. The last add() call adds the element at the beginning of the list and rest of elements are shifted.
you can access elements using get method. you need to specify the index of the element.
Again you can access elements via Iterator.
package org.codexplo.blog.list; import java.util.ArrayList; import java.util.Iterator; import java.util.List; public class AddingAndAccessingList { public static void main(String[] args) { List list = new ArrayList(); list.add("a"); list.add("b"); list.add("c"); list.add(0, "abcd"); // via get() method String a = (String) list.get(0);// need to type cast as I used generic // type List String b = (String) list.get(0); // via iterator Iterator iterator = list.iterator(); while (iterator.hasNext()) { String string = (String) iterator.next(); } } }
Removing Elements
You can remove element in two ways.
boolean remove(Object o); E remove(int index);
The first method removes the first occurrence of the specified element from the list. If the list does not contain the element, it is unchanged. More precisely it removes the element with lowest index if the element exist. Returns true if the list contained the specified element.
The second method removes element at the specified position in the list. It shift any subsequent elements to the left concurrently and return the element that was removed from the list.
package org.codexplo.blog.list; import java.util.*; public class RemoveListObject { public static void main(String[] args) { List list = new ArrayList(); list.add("a"); list.add("b"); list.add("c"); list.add("d"); list.remove("a"); list.remove(2); } }
These are the basic operation of the list. But there are some more methods available in List interface. Some of them are given shortly.
int size();
Returns the number of element in the list. int size(); If the list contains more than Integer.Max_Value elements, it returns Integer.Max_Value meaning if the list contain more than 2147483642, it will return 2147483647 because we know an int can can have, 2^31-1.
boolean isEmpty();
returns true if the list contains no element otherwise false.
boolean contains(Object o);
returns true the list contains the specified element.
Iterator<E> iterator();
Returns an iterator over the elements in the list in proper sequence.
Object[] toArray();
Returns an array containing all of the elements in the list in proper sequence (from first to last element).
void clear();
Removes all of the elements from this list (optional operation).
int indexOf(Object o);
Returns the index of the first occurrence of the specified element in the list, or -1 if this list does not contain the element.
int lastIndexOf(Object o);
Returns the index of the last occurrence of the specified element in this list, or -1 if this list does not contain the element.
List subList(int fromIndex, int toIndex);
Returns a view of the portion of this list between the specified fromIndex, inclusive, and toIndex, exclusive.
if you want to remove a subset of elements from the list, you can use following way.
list.subList(from, to).clear();
it will remove elements of the range specified.
Optimized technique.
The performance of different implementation of List is different. The choice of using list implementation depends on specific operation. As I said earlier, all list type support all basic operation, so which one to choose since all the list implementation support these basic operation? Here choice depends on the performance and requirement options.
The requirement operation could be –
1. Thread safety
2. Size of collection
3. Type of operation (adding, removing , accessing or iterating)
If you want your collection to be thread safe then Vector or Stack must be used because both have synchronized methods. ArrayList and LinkedList are not thread safe. Stack is mean fo LIFO (last in, first out) operation. If thread safety is not your concern, you can use ArrayList or LinkedList. From the performance point of view the ArrayList gives better gives better performance when accessing and iterating object whereas LinkedList gives better performance when adding and removing objects.
The initial size for ArrayList and Vector is 10. ArrayList increase its capacity by half approximately whenever its capacity reaches maximum(10) but vector increase its capacity by double whenever its capacity reaches maximum.
LinkedList gives good performance when adding elements at the end and beginning but it is worse when adding objects at middle because it needs to scan the node whenever it needs to add an object.
Iterating collection using all three types of classes ,ArrayList ,Vector and LinkedList gives similar performance.
Key Points:
1. Use ArrayList with proper initialization if you don’t want thread safe for the collection whenever you add/remove/access objects at end and middle of collection.
2. Use Vector with proper initialization if you want thread safe for the collection whenever you add/remove/access objects at end and middle of collection.
3. Use LinkedList if you don’t want thread safe for the collection whenever you add/remove/access objects at beginning of collection.
4. Use synchronized LinkedList if you want thread safe for the collection whenever you add/remove/access objects at beginning of collection.