Sunday, July 11, 2010

Puzzle 61 - Set for Optimization?

I'm back with an optimization question. Lately I've been dealing with some huge volume of data and I've realized how performance can start to be a serious problem as the data increases. Here is a small illustration with relatively less data (50,000 values). Hopefully the question should be self explanatory from the code.

package com.test; import java.util.List; import java.util.ArrayList; class MyCollection{ public static void populateList(List<Long> l, int multiple){ for(int i=0; i<50000; i++){ Long value = Long.valueOf(i*multiple); l.add(value); } } public static void main(String[] args) { List<Long> listOf2 = new ArrayList<Long>(); populateList(listOf2, 2); List<Long> listOf3 = new ArrayList<Long>(); populateList(listOf3, 3); long startTimestamp, endTimestamp; List<Long> commonA = null, commonB = null, commonC = null; //First Attempt - Runs in 60 seconds startTimestamp = System.currentTimeMillis(); commonA = new ArrayList<Long>(listOf2); commonA.retainAll(listOf3); endTimestamp = System.currentTimeMillis(); System.out.println("Execution Time : " + (endTimestamp-startTimestamp)/1000); //Second Attempt - Runs in 73 seconds - //There are fewer elements in commonB shouldn't this run faster? startTimestamp = System.currentTimeMillis(); commonB = new ArrayList<Long>(listOf3); commonB.retainAll(listOf2); endTimestamp = System.currentTimeMillis(); System.out.println("Execution Time : " + (endTimestamp-startTimestamp)/1000); System.out.println("Are Equal : " + (commonA.equals(commonB))); //Third Attempt - Runs in 2 seconds startTimestamp = System.currentTimeMillis(); /* This part has been intentionally left blank. * That is because I need to have a question for the puzzle, * and I felt like leaving out the Third part would be the right * thing do to. * I've done most of the hard work so this should be easy to fill. * Yes this must run 10 times faster than the solution I have provided * and should be done just as many lines (3 to 5 lines of code should be fine!). * Well I never said anything about life being fair, did I? * */ endTimestamp = System.currentTimeMillis(); System.out.println("Execution Time : " + (endTimestamp-startTimestamp)/1000); System.out.println("Are Equal : " + (commonA.equals(commonC))); } }


Just keep in mind that both the "Are Equal" print statements print true and that you don't use the reference commonA or commonB when writing the code for the third part. You are free to make any other changes (in the place where the comments are there).

Update - The commonA, commonB were incorrectly pointing to the objects listOf2/listof3. That has been corrected to create new Objects -- it now reads commonA = new ArrayList(listOf2); instead of commonA = listOf2;.
Thanks to Colin Hebert for pointing it out.

Puzzle 60 (Go Soft) - Solution

Last week we looked at soft-reference and the answer that naturally comes is what the Java Doc has to say about soft references "As long as the referent of a soft reference is strongly reachable, that is, is actually in use, the soft reference will not be cleared".
Looking at the code - we have strongly reachable reference to the MemoryIntensiveObject(), O and one would expect the soft reference to exists. However as Jeremy Manson points out in his blog, this might not necessarily be the case.

As mentioned before this question was based on the Jeremy Manson blog post.

Monday, July 5, 2010

Go Soft?

An interesting post that I read sometime ago rakes up this discussion. I'll add the reference to the original post next week.

To give a bit of background we first see what a SoftReference object is. SoftReference is an object which is cleared at the discretion of the garbage collector in response to memory demand. Soft references are most often used to implement memory-sensitive caches. An object that is reachable (only) from a SoftReference is eligible for Garbage collection. The java doc is pretty clear - I recommend reading it!

The problem is the pretty little three line code below,
Object someMethod() { Object o = new MemoryIntensiveObject(); SoftReference<MemoryIntensiveObject> ref = new SoftReference<MemoryIntensiveObject>(o); //Assume garbage collector at this point and needed to free up memory. return ref.get(); }


Is the soft reference bound to return the object that was originally pointed by o ?

Monday, June 28, 2010

More puzzles coming this way.

Its been over 6 months since I have posted here - mostly cause I ran out of stuff to post!! Well time to announce a come back. That's right folks next week (Sunday) onwards we'll start of with some POJP - thats Plain Old Java Puzzles!!

If anyone is wondering why today, do have a look at this one for a clue -- http://twisters.quiz4j.com/2009/06/puzzle-37-fun-with-strings-birthday.html