wood burning stoves 2.0*
The moose likes Threads and Synchronization and the fly likes Grappling with ConcurrentHashMap Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


Win a copy of Spring in Action this week in the Spring forum!
JavaRanch » Java Forums » Java » Threads and Synchronization
Bookmark "Grappling with ConcurrentHashMap" Watch "Grappling with ConcurrentHashMap" New topic
Author

Grappling with ConcurrentHashMap

Steven Rodeo
Ranch Hand

Joined: Mar 06, 2008
Posts: 72


HI folks,

Apologies, if this is trivial.

I am implementing a cache.

The KEY being a "String" and the VALUE being an List. I wrote this code to this effect.

Is this function thread safe ?. For instance what happens if another thread comes by and deletes a given mapping for a key.



Thanks Much
-SM
Winston Gutkowski
Bartender

Joined: Mar 17, 2011
Posts: 8008
    
  22

Steven Rodeo wrote:I am implementing a cache.
The KEY being a "String" and the VALUE being an List.

I guess my first question would be: why a List?
Since Lists allow duplicates, value could be added many times for the same key. Is that what you want?

I wrote this code to this effect.
Is this function thread safe ?.

Looks it; however, it seems a bit tortuous. How about just:
Winston


Isn't it funny how there's always time and money enough to do it WRONG?
Articles by Winston can be found here
Winston Gutkowski
Bartender

Joined: Mar 17, 2011
Posts: 8008
    
  22

Steven Rodeo wrote:Is this function thread safe?

It also occurred to me that if each entry in your cache was also a Concurrent collection, you could do the whole thing in one line, viz:

Winston
Mike Simmons
Ranch Hand

Joined: Mar 05, 2008
Posts: 3018
    
  10
Winston Gutkowski wrote:

But putIfAbsent() returns null if the key was not previously mapped.
Steven Rodeo
Ranch Hand

Joined: Mar 06, 2008
Posts: 72
This is going to throw a NullPointerException ?. I see this from the javadocs



  • Except that the action is performed atomically.

    Specified by: putIfAbsent in interface ConcurrentMap<K,V>

    Parameters:
    key - key with which the specified value is to be associated.
    value - value to be associated with the specified key.

    Returns:
    previous value associated with specified key, or null if there was no mapping for key.

    Throws:
    NullPointerException - if the specified key or value is null.
  • Winston Gutkowski
    Bartender

    Joined: Mar 17, 2011
    Posts: 8008
        
      22

    Mike Simmons wrote:
    Winston Gutkowski wrote:

    But putIfAbsent() returns null if the key was not previously mapped.

    Oh yeah. Duh. Seems to me they might have missed a beat there - I guess it's to keep it consistent with HashMap, but why return null when you don't have to?

    @Steven: My apologies. I guess it has to be:but I am right that if you use a Concurrent dataset you don't need the synchronized block.

    Winston
    Jeff Verdegan
    Bartender

    Joined: Jan 03, 2004
    Posts: 6109
        
        6

    I usually do it as:



    The tradeoff between an unneeded lookup and an unneeded object creation may be a bit of premature optimization in either direction, but I'll usually go with the first case (extra lookup).
    Winston Gutkowski
    Bartender

    Joined: Mar 17, 2011
    Posts: 8008
        
      22

    Jeff Verdegan wrote:The tradeoff between an unneeded lookup and an unneeded object creation may be a bit of premature optimization in either direction, but I'll usually go with the first case (extra lookup).

    Yeah, I guess if it's a cache, the first style might save you creating a lot of empty Lists (or V's) unnecessarily.

    Winston
    Pat Farrell
    Rancher

    Joined: Aug 11, 2007
    Posts: 4659
        
        5

    First thing I'd ask is why are you implementing a cache? There are lots of existing implementations that are free, open source, debugged, documented, etc.

    So if you want to learn, lets keep going. But if you just want to use one, I'd start with the Google Guava com.google.common.cache.* classes.

    Once you get the fundamentals working, you really need to thing long and hard about what strategies you want to use, when do you kick entries out of the cache, how often do you kick one or more out, what is the loading strategy, etc.

    The initial discussion of them usually start with a last used goes out first strategy, but that is not optimal in many real world usages.
     
    jQuery in Action, 2nd edition
     
    subject: Grappling with ConcurrentHashMap