教育机构网站建设,做的网站每年需要续费,运城市网站建设公司,廊坊百度快速排名JavaSE-线程池#xff08;1#xff09;- 线程池概念
前提
使用多线程可以并发处理任务#xff0c;提高程序执行效率。但同时创建和销毁线程会消耗操作系统资源#xff0c;虽然java 使用线程的方式有多种#xff0c;但是在实际使用过程中并不建议使用 new Thread 的方式手…JavaSE-线程池1- 线程池概念
前提
使用多线程可以并发处理任务提高程序执行效率。但同时创建和销毁线程会消耗操作系统资源虽然java 使用线程的方式有多种但是在实际使用过程中并不建议使用 new Thread 的方式手动创建线程。
线程池概念
线程池可以理解成一个存放线程的容器当需要使用线程处理任务时从线程池中取而并非直接创建一个线程
使用线程池的优势
降低资源消耗。通过重复利用已创建的线程降低线程创建和销毁造成的消耗。提高响应速度。当任务到达时任务可以不需要的等到线程创建就能立即执行。提高线程的可管理性。线程是稀缺资源如果无限制的创建不仅会消耗系统资源还会降低系统的稳定性使用线程池可以进行统一的分配调优和监控。
来自 《Java 并发编程的艺术》
线程池相关接口以及类
Runnable
可以理解成一个不需要获取返回结果的任务
FunctionalInterface
public interface Runnable {public abstract void run();
}Callable
类似于 Runnable 是一个有返回结果的任务
FunctionalInterface
public interface CallableV {/*** Computes a result, or throws an exception if unable to do so.** return computed result* throws Exception if unable to compute a result*/V call() throws Exception;
}Future
异步任务提交后使用 Future 接收从 Future get 方法可以获取异步任务的返回值
public interface FutureV {boolean cancel(boolean mayInterruptIfRunning);boolean isCancelled();boolean isDone();V get() throws InterruptedException, ExecutionException;V get(long timeout, TimeUnit unit)throws InterruptedException, ExecutionException, TimeoutException;
}RunnableFuture
Runnable 和 Future 的结合体
public interface RunnableFutureV extends Runnable, FutureV {/*** Sets this Future to the result of its computation* unless it has been cancelled.*/void run();
}FutureTask
RunnableFuture 接口的实现类
public class FutureTaskV implements RunnableFutureV {
}使用demo
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;public class FutureTaskTest {public static void main(String[] args) throws ExecutionException, InterruptedException {FutureTask futureTask new FutureTask(() - {Thread.sleep(1000);return 100;});new Thread(futureTask).start();System.out.println(futureTask.get());}
}Executor
执行器用来执行 Runnable 任务通过实现 Executor 接口可以自定义任务的执行方式比方使用线程池来执行任务避免使用 new Thread 的方式来执行
public interface Executor {/*** 执行方法执行一个具体的 Runnable 任务*/void execute(Runnable command);
}ExecutorService
继承自 Executor 提供更多的方法实现线程池的类一般继承这个接口
public interface ExecutorService extends Executor {/*** 关闭执行器但是会等待已经提交的任务执行完成不再接收新的任务*/void shutdown();/*** 尝试停止所有正在执行的任务不再接收新的任务*/ListRunnable shutdownNow();/***判断执行器是否关闭如果此执行器已关闭则返回true。*/boolean isShutdown();/*** 如果关闭后调用 shutdown 或 shutdownNow 方法所有任务都已完成则返回true。* 请注意除非首先调用shutdown或shutdownNow否则isTerminated 永远不会为true。*/boolean isTerminated();/*** Blocks until all tasks have completed execution after a shutdown* request, or the timeout occurs, or the current thread is* interrupted, whichever happens first.*/boolean awaitTermination(long timeout, TimeUnit unit)throws InterruptedException;/*** 提交一个有返回值的任务并使用 Future 接收*/T FutureT submit(CallableT task);/*** Submits a Runnable task for execution and returns a Future* representing that task. The Futures {code get} method will* return the given result upon successful completion.*/T FutureT submit(Runnable task, T result);/*** 提交任务并使用 Future 接收*/Future? submit(Runnable task);/*** Executes the given tasks, returning a list of Futures holding* their status and results when all complete.* {link Future#isDone} is {code true} for each* element of the returned list.* Note that a emcompleted/em task could have* terminated either normally or by throwing an exception.* The results of this method are undefined if the given* collection is modified while this operation is in progress.*/T ListFutureT invokeAll(Collection? extends CallableT tasks)throws InterruptedException;/*** Executes the given tasks, returning a list of Futures holding* their status and results* when all complete or the timeout expires, whichever happens first.* {link Future#isDone} is {code true} for each* element of the returned list.* Upon return, tasks that have not completed are cancelled.* Note that a emcompleted/em task could have* terminated either normally or by throwing an exception.* The results of this method are undefined if the given* collection is modified while this operation is in progress.*/T ListFutureT invokeAll(Collection? extends CallableT tasks,long timeout, TimeUnit unit)throws InterruptedException;/*** Executes the given tasks, returning the result* of one that has completed successfully (i.e., without throwing* an exception), if any do. Upon normal or exceptional return,* tasks that have not completed are cancelled.* The results of this method are undefined if the given* collection is modified while this operation is in progress.*/T T invokeAny(Collection? extends CallableT tasks)throws InterruptedException, ExecutionException;/*** Executes the given tasks, returning the result* of one that has completed successfully (i.e., without throwing* an exception), if any do before the given timeout elapses.* Upon normal or exceptional return, tasks that have not* completed are cancelled.* The results of this method are undefined if the given* collection is modified while this operation is in progress.*T T invokeAny(Collection? extends CallableT tasks,long timeout, TimeUnit unit)throws InterruptedException, ExecutionException, TimeoutException;
}AbstractExecutorService
public abstract class AbstractExecutorService implements ExecutorService {
}实现 ExecutorService 接口提供ExecutorService执行方法的默认实现
ThreadPoolExecutor
public class ThreadPoolExecutor extends AbstractExecutorService {
}线程池的具体实现类继承自 AbstractExecutorService
类结构图
ThreadPoolExecutor 使用方法
可以使用工具类 Executors 提供的方法创建线程池比如
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;public class ExecutorServiceTest1 {static class MyTask implements Runnable {private int i;public MyTask(int i) {this.i i;}Overridepublic void run() {try {Thread.sleep(2000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println(Thread.currentThread() 任务 i);}}public static void main(String[] args) {ExecutorService executorService Executors.newFixedThreadPool(2);for (int i 1; i 10; i) {executorService.execute(new MyTask(i));}executorService.shutdown();}
}以上 Executors.newFixedThreadPool 方法创建了一个拥有固定线程数的线城池
public static ExecutorService newFixedThreadPool(int nThreads) {return new ThreadPoolExecutor(nThreads, nThreads,0L, TimeUnit.MILLISECONDS,new LinkedBlockingQueueRunnable());
}执行结果
Thread[pool-1-thread-1,5,main] 任务1
Thread[pool-1-thread-2,5,main] 任务2
Thread[pool-1-thread-2,5,main] 任务4
Thread[pool-1-thread-1,5,main] 任务3
Thread[pool-1-thread-1,5,main] 任务6
Thread[pool-1-thread-2,5,main] 任务5
Thread[pool-1-thread-2,5,main] 任务8
Thread[pool-1-thread-1,5,main] 任务7
Thread[pool-1-thread-2,5,main] 任务9
Thread[pool-1-thread-1,5,main] 任务10通过结果可以看出10个任务都是由两个线程执行的由于这两个线程一次只能处理两个任务其他任务只有在线程空闲时才能被处理实际上线程池不仅维护了一组线程的引用还维护了这组任务而任务则是放在队列中即上文的 LinkedBlockingQueue 参数
参考 https://blog.csdn.net/qq_36881887/article/details/125707550 https://www.mianshigee.com/note/detail/20134hnk/