Friday, May 8, 2015

Sonic, What's up with your foam cups??

I have been noticing for the past few months that my Route 44 styrofoam cups from Sonic in OKC have the annoying 'feature' that they leak through the pores in the foam. I have noticed this many times - and is it ever annoying. Here is a sample from the cup I am using right now. This cup is probably two or three days old, picked up at the Bricktown Sonic:
Those little drops look like normal condensation, but they are actually water escaping through the cup. I have to keep a paper towel under my drink at all times or else my desk will be all wet. In years past I could keep the cups for a long time and this would not happen. Very strange and not a little annoying.

Monday, May 4, 2015

Java Synchronization. What's the big deal?

Throughout my career as a Java developer, I have read a non-trivial amount of code related to minimizing the impact of synchronized code blocks.  The topic of thread safety is extremely complex, and must be embarked upon carefully.  In some cases, just declaring lack of thread safety can simplify a project immensely, E.G., java swing, but there are times when it can't be avoided without introducing a lot of complexity on the other side of the API.  That's not what I am referring to, however.  Consider double-checked locking.  This technique is often used simply to reduce the amount of time it takes to call an accessor.  To illustrate, I wrote the following chunk of code:

import java.math.BigDecimal;
public class Main {
 public static final long TEST_COUNT = 1000000000L;
 public static void main(String[] args) {
 long r = 0;
 long startSync = System.currentTimeMillis();
 for (long i = 0; i < TEST_COUNT; i++)
 {
 r += getSync();
 }
 long stopSync = System.currentTimeMillis();
 long startUnsync = System.currentTimeMillis();
 for (long i = 0; i < TEST_COUNT; i++)
 {
 r += getUnSynch();
 }
 long stopUnsync = System.currentTimeMillis();
 BigDecimal syncTotal = new BigDecimal(stopSync - startSync);
 System.out.println("Sync took (" + syncTotal + ") ms., or (" + (syncTotal.divide(new BigDecimal(TEST_COUNT)).multiply(new BigDecimal(1000))) + ") microseconds average.");
 BigDecimal unsyncTotal = new BigDecimal(stopUnsync - startUnsync);
 System.out.println("Unsync took (" + unsyncTotal + ") ms., or (" + (unsyncTotal.divide(new BigDecimal(TEST_COUNT)).multiply(new BigDecimal(1000))) + ") microseconds average.");
 }
 private static synchronized long getSync()
 {
 return System.currentTimeMillis() % 100L;
 }
 private static long getUnSynch()
 {
 return System.currentTimeMillis() % 100L;
 }
}

When I ran it, this was my output:
Sync took (98345) ms., or (0.098345000) microseconds average.
Unsync took (43530) ms., or (0.04353000) microseconds average.


The difference here is 50 or so nanoseconds per access. Unless you are writing a high-performance application like a 3D game or database, I just don't see how this can even be worth discussing. Almost every application I write would involve calling these accessors on creation, which means 40 or 50 times during an entire application life, or even if it is tied to user requests like in a service or web application, 50 microseconds per request will be dwarfed by the amount of time the request itself takes. If there is a database access, just opening a connection that takes 1 millisecond to open will be 20,000 times slower than a synchronized accessor.

As engineers we sometimes like to focus on the really fun stuff, like generated bytecode or network packets or even CPU states, but synchronization overhead doesn't even seem like it's worth the time to type out.

PS: Have I said how much I hate the blogger editor???