线程--线程池篇

java 关于线程池的简单使用及注意点。

先来看下线程池的原理图吧,来了runnable请求,进行线程的创建,到coresize之后,会进行缓存(workqueue),当缓存已满,但最大线程数为到达的时候,会接着创建新的线程执行runnable。当线程执行完某个runnable之后,会从换从中取走,去执行。

当然,如果达到最大线程了,缓存也慢了,还在进行execute申请/或者是已经shutdown了,则会抛出异常,需要在code中进行捕捉或者设置处理策略。

下面是例子,注释中也囊括了所有的知识点:

注意点:1.如果已经提供的四中线程池方法满足需求,则尽量使用:(点击打开链接

2.如果不满足,需要new的,需要注意rejection的处理(4中策略,一种异常捕捉);

3.注意一下不同的queue的区别(ArrayBlockingQueue、LinkedBlockingQueue、SynchronousQueue)

public class TryExecutor extends Activity {

    private int QueueSize = 10;

    private int mCoreSize;
    private int mMaxSize;
    private int mKeepAliveTime;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        init();

    }

    private void init() {

        mCoreSize = Runtime.getRuntime().availableProcessors();// cpu core count;
        Log.d(TAG, "Current avaliable processor is: "+mCoreSize);
        mMaxSize = 2 * mCoreSize;// max poor size;
        mKeepAliveTime = 10;//alive time;

        //new ThreadPoolExecutor---ArrayBlockingQueue(FIFO)--which you must set queue size.
        ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(mCoreSize, mMaxSize,
                mKeepAliveTime, TimeUnit.SECONDS, new ArrayBlockingQueue <Runnable>(QueueSize));

        //new ThreadPoolExecutor--LinkedBlockingDeque(link FIFO)--which you can set queue size or not, if not the size is Integer.MAX_VALUE.
//        ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(mCoreSize, mMaxSize, mKeepAliveTime, TimeUnit.SECONDS,
//                new LinkedBlockingDeque <Runnable>());//new LinkedBlockingDeque <Runnable>(QueueSize));

        //new ThreadPoolExecutor--SynchronousQueue(NO queue).
//        ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(mCoreSize, mMaxSize, mKeepAliveTime, TimeUnit.SECONDS,
//                new SynchronousQueue <Runnable>());


        //Solve the reject error:
        //1. do noting == AbortPolicy:throw exception.
        //2.DiscardPolicy:drop
        //3.DiscardOldestPolicy: drop the oldeset one
        //4.CallerRunsPolicy: the thread who make executor handle. In this activity, it's the main thread.
        //5. new RejectedExecutionHandler to handle exception.
//        threadPoolExecutor.setRejectedExecutionHandler(new ThreadPoolExecutor.DiscardOldestPolicy());

//        threadPoolExecutor.setRejectedExecutionHandler(new RejectedExecutionHandler() {
//            @Override
//            public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
//                //TODO:
//            }
//        });

        //four executor for simple use:
        //1.newFixedThreadPool
        /*
        * public static ExecutorService newFixedThreadPool(int nThreads) {
        *        return new ThreadPoolExecutor(nThreads, nThreads,
        *               0L, TimeUnit.MILLISECONDS,
        *               new LinkedBlockingQueue<Runnable>());
        *       }
        */
        //2.newSingleThreadExecutor
        /*
        * public static ExecutorService newSingleThreadExecutor() {
        *        return new ThreadPoolExecutor(1, 1,
        *               0L, TimeUnit.MILLISECONDS,
        *               new LinkedBlockingQueue<Runnable>());
        *       }
        */
        //3.newCachedThreadPool
        /*
        * public static ExecutorService newCachedThreadPool() {
        *        return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
        *               60L, TimeUnit.SECONDS,
        *               new SynchronousQueue<Runnable>());
        *       }
        * */
        //4.newScheduledThreadPool
         /*
        * public static ExecutorService ScheduledThreadPoolExecutor(int corePoolSize) {
        *        return new ThreadPoolExecutor(corePoolSize, Integer.MAX_VALUE,
        *               10L, TimeUnit.MILLISECONDS,
        *               new DelayedWorkQueue());
        *       }
        * */
//        ExecutorService fixedThreadPool = Executors.newFixedThreadPool(mCoreSize);
//        ExecutorService singleThreadExecutor = Executors.newSingleThreadExecutor();
//        ExecutorService cachedThreadPool = Executors.newCachedThreadPool();
//        ExecutorService scheduledThreadPool = Executors.newScheduledThreadPool(mCoreSize);


        int i = 0;
        while (i++<15) {
            MyTask task = new MyTask(i);
            threadPoolExecutor.execute(task);

//            fixedThreadPool.execute(task);
//            singleThreadExecutor.execute(task);
//            cachedThreadPool.execute(task);
//            scheduledThreadPool.execute(task);

            Log.d(TAG, "current core pool size: "+threadPoolExecutor.getCorePoolSize() +
                    ", completed task count: "+threadPoolExecutor.getCompletedTaskCount() +
                    ", active count: "+threadPoolExecutor.getActiveCount() +
                    ", pool size: "+threadPoolExecutor.getPoolSize() +
                    ", task count: "+threadPoolExecutor.getTaskCount());
        }

        threadPoolExecutor.allowsCoreThreadTimeOut();
        while (threadPoolExecutor.getActiveCount() != 0) {
            Thread.yield();
        }
        threadPoolExecutor.shutdownNow();
        Log.d(TAG, "Shut down!");
    }


    class MyTask implements Runnable {

        private int index;

        public MyTask(int index) {
            this.index = index;
        }

        @Override
        public void run() {
            try {
                Thread.currentThread().sleep(20);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            Log.d(TAG,"current thread is: "+Thread.currentThread().getName() + ", index: "+index);
        }
    }

}

如果看的懵逼,建议先看一下这篇文章,基础概念都有比较好讲解:点击打开链接

源码获取:点击打开链接

https://github.com/shixin398/MultiThreadDemo

其中还有创建线程,停止线程,线程同步方法,同时启动线程个数的控制,及当前文章的相应code;

对于thread 使用较多的知识的一个概括介绍。

猜你喜欢

转载自blog.csdn.net/shi_xin/article/details/79788740