位置:java/util/concurrent(多线程并发,J.U.C): 接口: Callable(类似Runnable), Executor(线程池), Future(线程执行结果), FutureTask(线程任务), Excutors(线程池工厂,可创建ExecutorService)。。。
这里的并发是针对多线程而言的,在java中创建线程有四种方式: 1)继承Thread类 2)实现Runnable接口 3)使用Executor线程池创建 4)实现Callable接口
其中3和4是针对多线程的。
位置:java/util/concurrent/locks/(锁相关) 相关接口: Condition(封装对象object的监视方法如wait,notify等), Lock, ReadWriteLock, ReentrantLock。。。
在没有锁的api之前,锁的实现主要使用synchronized,该关键字利用的是每个对象都有的隐式监视锁。但不够灵活,所以有了新的API。 锁是为了在多个线程同时访问同一共享资源的时候采取的策略,此时只有得到该资源对应唯一锁的线程可以操作资源,其他线程直到占有该锁的线程释放该锁后才可以访问对应资源。 当然,有的锁实现比如读写锁可以允许几个线程同时访问资源,如读取与写入同时进行。
本文将讲解Future,ExecutorService,Callable的使用:
import java.util.ArrayList; import java.util.Date; import java.util.List; import java.util.concurrent.*; public class MyCallable implements Callable<String> { @Override public String call() throws Exception { Thread.sleep(1000);//暂停1s return Thread.currentThread().getName();//获取当前线程名称,线程被执行时该方法返回String并封装在Future接口中。 } public static void main(String[] args) throws ExecutionException, InterruptedException { ExecutorService executorService = Executors.newFixedThreadPool(10);//创建大小为10的线程池 List<Future<String>> list = new ArrayList<Future<String>>();//存储线程处理结果 Callable<String> callable = new MyCallable(); for (int i = 0; i < 50; i++) { Future<String> future = executorService.submit(callable);//线程池只有10,要执行50个线程,分50/10=5次进行,每进行完10个callable后重新调用call(),因此每执行输出10行就会等1s。 list.add(future); } for (Future<String> fut : list) { System.out.println(new Date() + "::" + fut.get()); } executorService.shutdown();//别忘了要关闭线程池哦 } }结果如下,从结果也可以看出执行过程并不是同步顺序的:
Sat Feb 17 14:59:47 CST 2018::pool-1-thread-1 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-2 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-3 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-4 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-5 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-6 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-7 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-8 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-9 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-10 Sat Feb 17 14:59:48 CST 2018::pool-1-thread-3 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-4 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-2 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-5 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-1 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-6 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-8 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-7 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-9 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-10 Sat Feb 17 14:59:49 CST 2018::pool-1-thread-9 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-10 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-7 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-8 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-6 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-1 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-5 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-2 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-4 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-3 Sat Feb 17 14:59:50 CST 2018::pool-1-thread-3 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-4 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-2 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-5 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-1 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-6 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-8 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-7 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-10 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-9 Sat Feb 17 14:59:51 CST 2018::pool-1-thread-3 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-4 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-2 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-5 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-1 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-6 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-8 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-7 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-10 Sat Feb 17 14:59:52 CST 2018::pool-1-thread-9以上就是对Callable和ExecutorService的简单使用,后续会发一些深入的文章。