Ugly optimized caching of SimpleDateFormat Concerning the optimization of this simple function

String formatDate(String format, Locale locale, Date date) {...}


formatting a Date using a SimpleDateFormat created with the arguments format and locale. I'm curious  what you thing about the code below. I know it's terrible, but let's assume two things


The code must be as fast as possible.
There's no suitable object to hold the cache.
It must not cause any memory leaks.


Because of 1., a thread local cache should be used. However, the passed format and arguments may differ from those used in the cache and this must be checked. Funnily, although SimpleDateFormat is mutable (which is the cause of all problems), there seem to be no way how to change its format or locale. Actually, the parameters hardly ever change, but there's no guarantee.

Because of 2., the cache must be a static field.

Because of 3., no ThreadLocal.initialValue can be used as it'd lead to memory leaks just like in this question. For the same reason no custom class may be put into the ThreadLocal.

This all is pretty restrictive. So I wrote the following ugliness

private String toString(Date obj, String format, Locale locale) {
    return getSimpleDateFormat(format, locale).format(obj);
}

private SimpleDateFormat getSimpleDateFormat(String format, Locale locale) {
    Object[] list = SDF.get();
    // An identity check is faster and correct as missing an entry is allowed.
    // It's surely good enough as passing equals but not same parameters hardly ever happens.
    if (list!=null &amp;&amp; list[0] == format &amp;&amp; list[1] == locale) {
        return (SimpleDateFormat) list[2];
    }
    final SimpleDateFormat result = new SimpleDateFormat(format, locale);
    list = new Object[] {format, locale, result};
    SDF.set(list);
    return result;
}

/** Contains triples (String format, Locale locale, SimpleDateFormat sdf) */
private static final ThreadLocal&lt;Object[]&gt; SDF = new ThreadLocal&lt;Object[]&gt;();


I don't care about naming and such, as this was just a quick implementation of an idea. I'm curious if there's a substantially better solution satisfying all the above conditions.

If you say, it's premature optimization, I'll fully agree, but let's assume for a while it must be done. If you say, that's hardly faster than no caching, then show me your figures.



Obviously, I'm caching just one value per thread. It should be enough in many cases like producing a CSV with one one or more dates per row as I haven't yet see them to be formatted differently.

However, time is "date" too (at least in Java), and a CSV line containing both date and time in separate columns is rather common and this would render my poor man's cache fully ineffective.
What about using a WeakHashMap?  The memory leak is not really an issue since the memory can be reclaimed at any time.

Also, if I were using a map, I would define a FormatAndLocale util class, with valid hashCode and equals, to be used as keys.