2012-05-26 3 views
0

Постановка задачи: -Повышение эффективности для каждого потока, используя различные уникальный идентификатор

Каждый поток использует уникальный идентификатор в диапазоне от 1 до 1000 и программа должна работать в течение 60 минут или больше, так что в 60 минут, возможно, что все идентификаторы будут закончены, поэтому мне нужно снова использовать эти ID,

Я знаю несколько способов сделать это, одним из способов является то, что я написал, обратившись за помощью из StackOverflow, но когда я попытался запустить это, я обнаружил, что после нескольких минут работы эта программа становится очень медленной и для распечатки идентификатора на консоли требуется много времени. А также иногда получаю ошибку OutOfMemory. Есть ли лучший способ решить эту проблему?

class IdPool { 
    private final LinkedList<Integer> availableExistingIds = new LinkedList<Integer>(); 

    public IdPool() { 
     for (int i = 1; i <= 1000; i++) { 
      availableExistingIds.add(i); 
     } 
    } 

    public synchronized Integer getExistingId() { 
     return availableExistingIds.removeFirst(); 
    } 

    public synchronized void releaseExistingId(Integer id) { 
     availableExistingIds.add(id); 
    } 
} 


class ThreadNewTask implements Runnable { 
    private IdPool idPool; 

    public ThreadNewTask(IdPool idPool) { 
     this.idPool = idPool; 
    } 

    public void run() { 
     Integer id = idPool.getExistingId(); 
     someMethod(id); 
     idPool.releaseExistingId(id); 
    } 

    private void someMethod(Integer id) { 
     System.out.println("Task: " +id); 
    } 
} 

public class TestingPool { 
    public static void main(String[] args) throws InterruptedException { 
     int size = 10; 
     int durationOfRun = 60; 
     IdPool idPool = new IdPool(); 
     // create thread pool with given size 
     // create thread pool with given size 
    ExecutorService service = new ThreadPoolExecutor(size, size, 500L, TimeUnit.MILLISECONDS, new ArrayBlockingQueue<Runnable>(10), new ThreadPoolExecutor.CallerRunsPolicy()); 


     // queue some tasks 
     long startTime = System.currentTimeMillis(); 
     long endTime = startTime + (durationOfRun * 60 * 1000L); 

     // Running it for 60 minutes 
     while(System.currentTimeMillis() <= endTime) { 
      service.submit(new ThreadNewTask(idPool)); 
     } 

     // wait for termination   
     service.shutdown(); 
     service.awaitTermination(Long.MAX_VALUE, TimeUnit.DAYS); 
    } 
} 

ответ

4

Я уже объяснил вам в предыдущем вопросе, что ваш код, представленные миллионы и миллионы задач исполнителя, поскольку она представляет задачи в цикле в течение 60 минут, withot ждет.

Очень непонятно, какова конечная цель, но как вы, вы заполняете очередь задач, пока у вас больше нет памяти. Поскольку вы не объясняете цель своей программы, трудно дать вам какое-либо решение.

Но первое, что вы могли бы сделать, это ограничить размер очереди задач вашего исполнителя. Это заставит основной поток блокироваться каждый раз, когда очередь заполнена.

+0

Да, я бы установил количество потоков для запуска как точное количество ядер на CPU. –

+0

Моя конечная цель - программа должна работать в течение определенного количества минут, и каждый поток должен использовать разные уникальные идентификаторы между двумя номерами (от 1 до 1000 или может быть любым двумя номерами) и должен передать этот уникальный идентификатор определенному метод и использовать это число для выполнения определенной задачи. И как я могу ограничить размер очереди задач моего исполнителя? – AKIWEB

+0

Это не то, что я бы назвал конечной целью. Это набор произвольных ограничений без каких-либо проблем. Учитывая эти ограничения, вы можете запустить 10 потоков, каждый из которых имеет уникальный идентификатор, и цикл за 60 минут записывается в System.out. –

Смежные вопросы