线程池

2018-12-23  本文已影响0人  wanggs

1、为什么用线程池?

2、线程池参数的意思?

比如去火车站买票, 有10个售票窗口, 但只有5个窗口对外开放. 那么对外开放的5个窗口称为核心线程数, 而最大线程数是10个窗口.如果5个窗口都被占用, 那么后来的人就必须在后面排队, 但后来售票厅人越来越多, 已经人满为患, 就类似于线程队列已满.这时候火车站站长下令, 把剩下的5个窗口也打开, 也就是目前已经有10个窗口同时运行. 后来又来了一批人,10个窗口也处理不过来了, 而且售票厅人已经满了, 这时候站长就下令封锁入口,不允许其他人再进来, 这就是线程异常处理策略.而线程存活时间指的是, 允许售票员休息的最长时间, 以此限制售票员偷懒的行为

3.ThreadPoorExecutor原理?

image.png 20180419002550514.jpg
// 无边界队列,没有长度
        ConcurrentLinkedQueue clq = new ConcurrentLinkedQueue();
        // 入队
        clq.add(1);
        clq.add(2);
        clq.add(3);
        // 出对 并且在队列中移除
        System.out.println(clq.poll());
        System.out.println("队列数: " + clq.size());
        // 出对 不在队列移除
        System.out.println(clq.peek());
        System.out.println("队列数: " + clq.size());
        /**
         * 输出:
         * 1
         * 队列数: 2
         * 2
         * 队列数: 2
         */
         
         
 // 有界队列
        BlockingDeque bd = new LinkedBlockingDeque(2);
        // 入队
        bd.add(1);
        bd.add(2);
        System.out.println(bd.poll());
        // 3秒内是否放入进去
        bd.offer(3,3, TimeUnit.SECONDS);
        // 出对 并且在队列中移除
        System.out.println(bd.poll());
        System.out.println(bd.poll());
        System.out.println(bd.poll());

        /**
         * 1
         * 2
         * 3
         * null
         */
image.png

4、线程池实现

   public static void main(String[] args) throws InterruptedException {
        ThreadPoolExecutor tpe = new ThreadPoolExecutor(1,2,3,TimeUnit.SECONDS,new LinkedBlockingDeque<>(1));
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.shutdown();
        /**
         * pool-1-thread-1
         * pool-1-thread-2
         * pool-1-thread-1
         */
    }

5、线程池实现

 ThreadPoolExecutor tpe = (ThreadPoolExecutor) Executors.newFixedThreadPool(2);
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.shutdown();
ThreadPoolExecutor tpe = (ThreadPoolExecutor) Executors.newCachedThreadPool();
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.execute(new ThreadTest());
        tpe.shutdown();
 ScheduledExecutorService ses = Executors.newScheduledThreadPool(2);
        for (int i = 0; i < 10; i++) {
            ses.schedule(new ThreadTest(), 3, TimeUnit.SECONDS);
        }

        ses.shutdown();
/**
 * 3秒之后执行
 * pool-1-thread-1
 * pool-1-thread-2
 * pool-1-thread-1
 * pool-1-thread-2
 * pool-1-thread-1
 * pool-1-thread-2
 * pool-1-thread-2
 * pool-1-thread-1
 * pool-1-thread-2
 * pool-1-thread-1
 */
    }
        ExecutorService es = Executors.newSingleThreadExecutor();
        es.execute(new ThreadTest());
        es.execute(new ThreadTest());
        es.execute(new ThreadTest());
        es.shutdown();
/**
 * pool-1-thread-1
 * pool-1-thread-1
 * pool-1-thread-1
 */
image.png

6、用过threadlocal吗?怎么用的

订单处理包含一系列操作: 减少库存,增加一条流水账,修改总账,这几个操作要在同一个事务中操作,通常也就是在一个线程中处理,如果累加公司操作失败了,应把前面操作的回滚 ,否则提交所有操作,这要求这些操作使用相同的数据库连接对象,,而这些操作代码不在一个模块中。

image.png image.png

7, volatile

共享变量的可见性

每个线程都有自己本地的内存空间,线程执行的时候先把变量从内存中读取到自己的内存空间中,然后对变量进行操作,对变量操作完成后,在某个时间再把变量刷新到主内存中

image.png
public class TestVolatile {
    
    public static void main(String[] args) {
        ThreadDemo td = new ThreadDemo();
        new Thread(td).start();
        while(true){
            if(td.isFlag()){
                System.out.println("------------------");
                break;
            }
        }
    }

}

class ThreadDemo implements Runnable {
    private  boolean flag = false;
    @Override
    public void run() {
        try {
            Thread.sleep(200);
        } catch (InterruptedException e) {
        }
        flag = true;
        System.out.println("flag=" + isFlag());
    }

    public boolean isFlag() {
        return flag;
    }
}
Java中volatile、synchronized和lock解析
Java中volatile
上一篇下一篇

猜你喜欢

热点阅读