2016-08-09 77 views
1

我有一个固定大小的线程池12.现在我有两个类实现Runnable和每个类的20个对象。我可以提交所有任务,并且线程池将按常规执行其任务。在两个类之间共享一个线程池

我想要做的是做一个分隔符。因此,如果我提交了这40个任务,线程池将不会同时处理每个类的6个以上。因此,线程池的行为就像2个较小的6线程池。可以通过java或番石榴的API吗?

+0

是否可以创建两个大小为6的池? – Fildor

+0

如果我正确理解你的问题,我想你想知道线程池中有多少个活动线程,然后分隔它们,试试[''ThreadPoolExecutor.getActiveCount();'](http://docs.oracle.org/ .com/javase/7/docs/api/java/util/concurrent/ThreadPoolExecutor.html#getActiveCount%28%29) – px06

+0

@ px06如果您知道有关问题中所述要求的活动计数,您赢得了什么? – Fildor

回答

0

不用质疑“为什么” - 它可以通过使用信号量来实现,每个信号量的计数为6,每个信号量可以同时将每种类型的任务数量确定为6。

下面是一个基本工作示例:

public class TaskDelimitingTest { 

    private enum Tasks {TASK1, TASK2}; 

    private static ConcurrentHashMap<Tasks, AtomicInteger> taskObserver = new ConcurrentHashMap<>(); 

    public static class Task implements Runnable { 

    private static final Random random = new Random(System.currentTimeMillis()); 

    private final Semaphore sem = new Semaphore(6, true); 
    private final Tasks task; 

    public Task(Tasks task) { 
     this.task = task; 
    } 

    @Override 
    public void run() { 
     try { 
     taskObserver.get(task).incrementAndGet(); 
     Thread.sleep(random.nextInt(1000)); 
     taskObserver.get(task).decrementAndGet(); 
     sem.release(); 
     } catch (InterruptedException e) { 
     e.printStackTrace(); 
     } 
    } 

    public void postToExecution(ExecutorService executor) { 
     try { 
     sem.acquire(); 
     executor.execute(this); 
     } catch (InterruptedException e) { 
     e.printStackTrace(); 
     } 
    } 
    } 

    public static class Task1 extends Task { 

    public Task1() { 
     super(Tasks.TASK1); 
    } 

    } 

    public static class Task2 extends Task { 

    public Task2() { 
     super(Tasks.TASK2); 
    } 

    } 

    public static void main(String[] args) { 
    ExecutorService executor = Executors.newFixedThreadPool(12); 

    Thread t1 = new Thread(() -> { 
     taskObserver.put(Tasks.TASK1, new AtomicInteger()); 
     IntStream.rangeClosed(1, 100).forEach(i -> { 
     new Task1().postToExecution(executor); 
     System.out.println(taskObserver); 
     }); 
    }); 
    Thread t2 = new Thread(() -> { 
     taskObserver.put(Tasks.TASK2, new AtomicInteger()); 
     IntStream.rangeClosed(1, 100).forEach(i -> { 
     new Task2().postToExecution(executor); 
     System.out.println(taskObserver); 
     }); 
    }); 
    t1.start(); 
    t2.start(); 
    } 

} 

在这个例子中,我在两个单独的线程创建的每个两种类型的100个任务,让他们互相竞争,我也把Thread.sleeprun方法中,以便它们模拟不同的执行时间。

这个PROGRAMM的输出是 - 在“热身”阶段

{TASK2=1, TASK1=1} 
    ... 
    {TASK2=2, TASK1=3} 
    ... 
    {TASK2=4, TASK1=3} 
    ... 
    {TASK2=4, TASK1=4} 
    ... 
    {TASK2=4, TASK1=5} 
    ... 

在一段时间内的游泳池被饱和,然后它会只喜欢:最大于是才有

{TASK2=6, TASK1=6} 
    ... 

每种类型的6个线程正在同时执行。

相关问题