Baraa Natour
Baraa Natour

Reputation: 69

Synchronization and Semaphore

I am Looping through a Map , and i have a number of threads. the queue in the map contains Actions. my goal is to give every thread an Action to do.. but no 2 threads(or more) can run 2 task(or more) from one queue it means every thread is gonna search for a queue , and Lock the Queue some how and check if the queue has actions if yes it runs one of them if no search for another Queue to run fro them actions. NOTE: number of Queues can be greater than Number of Threads e I tried to synchronize on the 'Map.Entry'

        public void run() {

            while (true) {
                Action<?> act;
                for (Map.Entry entry :ActionMap.entrySet()) {
                   Synchronized(entry)
                   {
                      act =  ((Queue<Action>)entry.getValue()).poll();
                      if (act == null)
                        break;
                   }
                }

            }
            }  

the problem is that if another thread is searching for an action to do is gonna be stuck in the synchronized Line And Wait for the first thread to finish the task or to finish waiting and that is not what i want. i want all of the threads to search for queues if some a thread reaches a queue that another thread is working on just skip it and continue searching

so I digged around and found semaphore so I reached this

Semaphore Gate = new Semaphore(1);



        public void run() {

            while (true) {
                Action<?> act;
                for (Map.Entry entry :ActionMap.entrySet()) {
                   if( Gate.tryAcquire());
                   {
                      act =  ((Queue<Action>)entry.getValue()).poll();
                      if (act == null){
                    Gate.Release();
                    break;

                      }
                      else {
                      act.handle();
                      Gate.Release();
                    }
                   }
                }

            }
            }

put the problem with this that Gate.aquire() is gonna Lock all entries it means for 2 diffirent entries and 2 different threads only one thread can access the gate and execute the Action

so finally dose any one have a design pattern that can help me ? thank you ...

Upvotes: 0

Views: 521

Answers (1)

Gabriel Slomka
Gabriel Slomka

Reputation: 1527

You could use java.util.concurrent types of map for this. They are thread safe, so you dont need Syncronize.

Synchronize means : the resource(which is synchronized) can't be modified by multiple threads simultaneously. e.g MAP returned by Collections.synchronizedMap(Map) will be a synchronized map and can be modified by one thread at a time, but Concurrent Collections allows multiple threads to access different parts of a collection at a given time, based on the requirement. e.g we have an overloaded constructor for ConcurentHashMap which takes input concurrencyLevel as number of threads which can access the collection simultaneously.

Upvotes: 1

Related Questions