This is what I am doing:
String one = "some string"
String two = "some string"
I want to know all the characters that are in string one and two and they should come in order as they are in string one
I wrote a Java program which by using Collections performs set operations on both the collection.
What I would like to know that what is the complexity of performing set operations, is it polynomial time or linear time
My program is here
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package careercup.google;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
/**
*
* @author learner
*/
public class CharaterStringsIntersection {
private static final String one = "abcdefgabcfmnx";
private static final String two = "xbcg";
public static void main(String args[]){
List<Character> l_one = new ArrayList<Character>();
List<Character> l_two = new ArrayList<Character>();
for(int i=0; i<one.length(); i++){
l_one.add(one.charAt(i));
}
for(int j=0; j<two.length(); j++){
l_two.add(two.charAt(j));
}
l_one.retainAll(l_two);
Iterator iter = l_one.iterator();
while(iter.hasNext()){
System.out.println(" > " + iter.next());
}
}
}
Output :
run:
> b
> c
> g
> b
> c
> x
I think the more important question you are trying to ask is what is the complexity of retainAll() function. Assuming there are no hashes or quick look up, I would assume the time complexity is O(n^2). One loop to iterate the list and one loop to compare each item.
Its complexity is O(N * (N + M)), where N =
one.length()
, M =two.length()
.It works in the following way: for each character of
l_one
(there are N of them) it scansl_two
(sincel_two
is anArrayList
, scan is linear, so it takes O(M) steps, see [1]) and removes item froml_one
if necessary (removing fromArrayList
takes O(N), see [1]), so you get O(N * (N + M)).You can lower the complexity to O(N * M) by using
LinkedList
forl_one
(since removing fromLinkedList
is O(1), see [2]), and further lower it to O(N * log(M)) by usingTreeSet
forl_two
(since searching inTreeSet
takes O(log(M)), see [3]).References:
ArrayList
javadoc)LinkedList
javadoc)add
,remove
andcontains
) (TreeSet
javadoc)You are using the wrong collection for your purposes..
Since you are doing it with plain
ArrayList
the complexity wouldn't be good, I don't know the inner implementation but I would guess it's quadratic (since it has to scroll both lists), this unless Java internally converts two lists to sets before doing the intersection.You should start from
Set
interface (here) and choose which collection is more suitable for your needs, I think that aHashSet
(constant time) or aTreeSet
(logarithmic but able to keep natural ordering) would be best solutions.Briefly:
ArrayList.add()
isO(1)
.ArrayList.retainAll(other)
isO(N1 * N2)
whereN1
is the size ofthis
andN2
is the size ofother
. (The actual cost depends on the ratio of elements retained to elements removed.)iter.hasNext()
anditer.next()
areO(1)
for anArrayList
iterator.This is all as you would expect, based on mentally modelling an ArrayList as a Java array.