Added tests for yang.model.util
[yangtools.git] / common / util / src / main / java / org / opendaylight / yangtools / util / concurrent / SpecialExecutors.java
1 /*
2  * Copyright (c) 2014 Brocade Communications Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 package org.opendaylight.yangtools.util.concurrent;
10
11 import java.util.concurrent.ExecutorService;
12 import java.util.concurrent.ThreadPoolExecutor;
13 import java.util.concurrent.TimeUnit;
14
15 /**
16  * Factory methods for creating {@link ExecutorService} instances with specific configurations.
17
18  * @author Thomas Pantelis
19  */
20 public final class SpecialExecutors {
21
22     private SpecialExecutors() {
23     }
24
25     /**
26      * Creates an ExecutorService with a specified bounded queue capacity that favors creating new
27      * threads over queuing, as the former is faster, so threads will only be reused when the thread
28      * limit is exceeded and tasks are queued. If the maximum queue capacity is reached, subsequent
29      * tasks will be rejected.
30      * <p>
31      * For example, if the maximum number of threads is 100 and 100 short-lived tasks are submitted
32      * within say 10 seconds, then 100 threads will be created and used - previously constructed
33      * idle threads will not be reused. This provides the fastest execution of the 100 tasks at the
34      * expense of memory and thread resource overhead. Therefore it is advisable to specify a
35      * relatively small thread limit (probably no more than 50).
36      * <p>
37      * Threads that have not been used for 15 seconds are terminated and removed from the pool.
38      * Thus, a pool that remains idle for long enough will not consume any resources.
39      * <p>
40      * If you need an executor with less memory and thread resource overhead where slower execution
41      * time is acceptable, consider using {@link #newBoundedCachedThreadPool }.
42      *
43      * @param maximumPoolSize
44      *            the maximum number of threads to allow in the pool. Threads will terminate after
45      *            being idle for 15 seconds.
46      * @param maximumQueueSize
47      *            the capacity of the queue.
48      * @param threadPrefix
49      *            the name prefix for threads created by this executor.
50      * @return a new ExecutorService with the specified configuration.
51      */
52     public static ExecutorService newBoundedFastThreadPool( int maximumPoolSize,
53             int maximumQueueSize, String threadPrefix ) {
54         return new FastThreadPoolExecutor( maximumPoolSize, maximumQueueSize, threadPrefix );
55     }
56
57     /**
58      * Creates an ExecutorService similar to {@link #newBoundedFastThreadPool } except that it
59      * handles rejected tasks by running them in the same thread as the caller. Therefore if the
60      * queue is full, the caller submitting the task will be blocked until the task completes. In
61      * this manner, tasks are never rejected.
62      *
63      * @param maximumPoolSize
64      *            the maximum number of threads to allow in the pool. Threads will terminate after
65      *            being idle for 15 seconds.
66      * @param maximumQueueSize
67      *            the capacity of the queue.
68      * @param threadPrefix
69      *            the name prefix for threads created by this executor.
70      * @return a new ExecutorService with the specified configuration.
71      */
72     public static ExecutorService newBlockingBoundedFastThreadPool( int maximumPoolSize,
73             int maximumQueueSize, String threadPrefix ) {
74
75         FastThreadPoolExecutor executor =
76                 new FastThreadPoolExecutor( maximumPoolSize, maximumQueueSize, threadPrefix );
77         executor.setRejectedExecutionHandler( new ThreadPoolExecutor.CallerRunsPolicy() );
78         return executor;
79     }
80
81     /**
82      * Creates an ExecutorService with a specified bounded queue capacity that favors reusing
83      * previously constructed threads, when they are available, over creating new threads. When a
84      * task is submitted, if no existing thread is available, a new thread will be created and added
85      * to the pool. If there is an existing idle thread available, the task will be handed to that
86      * thread to execute. If the specified maximum thread limit is reached, subsequent tasks will be
87      * queued and will execute as threads become available. If the maximum queue capacity is
88      * reached, subsequent tasks will be rejected.
89      * <p>
90      * Threads that have not been used for sixty seconds are terminated and removed from the pool.
91      * Thus, a pool that remains idle for long enough will not consume any resources.
92      * <p>
93      * By reusing threads when possible, this executor optimizes for reduced memory and thread
94      * resource overhead at the expense of execution time.
95      * <p>
96      * If you need an executor with faster execution time where increased memory and thread resource
97      * overhead is acceptable, consider using {@link #newBoundedFastThreadPool }.
98      *
99      * @param maximumPoolSize
100      *            the maximum number of threads to allow in the pool. Threads will terminate after
101      *            being idle for 60 seconds.
102      * @param maximumQueueSize
103      *            the capacity of the queue.
104      * @param threadPrefix
105      *            the name prefix for threads created by this executor.
106      * @return a new ExecutorService with the specified configuration.
107      */
108     public static ExecutorService newBoundedCachedThreadPool( int maximumPoolSize,
109             int maximumQueueSize, String threadPrefix ) {
110         return new CachedThreadPoolExecutor( maximumPoolSize, maximumQueueSize, threadPrefix );
111     }
112
113     /**
114      * Creates an ExecutorService similar to {@link #newBoundedCachedThreadPool } except that it
115      * handles rejected tasks by running them in the same thread as the caller. Therefore if the
116      * queue is full, the caller submitting the task will be blocked until the task completes. In
117      * this manner, tasks are never rejected.
118      *
119      * @param maximumPoolSize
120      *            the maximum number of threads to allow in the pool. Threads will terminate after
121      *            being idle for 60 seconds.
122      * @param maximumQueueSize
123      *            the capacity of the queue.
124      * @param threadPrefix
125      *            the name prefix for threads created by this executor.
126      * @return a new ExecutorService with the specified configuration.
127      */
128     public static ExecutorService newBlockingBoundedCachedThreadPool( int maximumPoolSize,
129             int maximumQueueSize, String threadPrefix ) {
130
131         CachedThreadPoolExecutor executor =
132                 new CachedThreadPoolExecutor( maximumPoolSize, maximumQueueSize, threadPrefix );
133         executor.setRejectedExecutionHandler( new ThreadPoolExecutor.CallerRunsPolicy() );
134         return executor;
135     }
136
137     /**
138      * Creates an ExecutorService that uses a single worker thread operating off a bounded queue
139      * with the specified capacity. Tasks are guaranteed to execute sequentially, and no more than
140      * one task will be active at any given time. If the maximum queue capacity is reached,
141      * subsequent tasks will be rejected.
142      *
143      * @param maximumQueueSize
144      *            the capacity of the queue.
145      * @param threadPrefix
146      *            the name prefix for the thread created by this executor.
147      * @return a new ExecutorService with the specified configuration.
148      */
149     public static ExecutorService newBoundedSingleThreadExecutor( int maximumQueueSize,
150             String threadPrefix ) {
151         return new FastThreadPoolExecutor( 1, maximumQueueSize, Long.MAX_VALUE, TimeUnit.SECONDS,
152                 threadPrefix );
153     }
154 }