线程执行者(三)创建一个大小固定的线程执行者

创建一个大小固定的线程执行者

当你使用由Executors类的 newCachedThreadPool()方法创建的基本ThreadPoolExecutor,你会有执行者运行在某一时刻的线程数的问题。这个执行者为每个接收到的任务创建一个线程(如果池中没有空闲的线程),所以,如果你提交大量的任务,并且它们有很长的(执行)时间,你会使系统过载和引发应用程序性能不佳的问题。

如果你想要避免这个问题,Executors类提供一个方法来创建大小固定的线程执行者。这个执行者有最大线程数。 如果你提交超过这个最大线程数的任务,这个执行者将不会创建额外的线程,并且剩下的任务将会阻塞,直到执行者有空闲线程。这种行为,保证执行者不会引发应用程序性能不佳的问题。

在这个指南中,你将继续学习怎样创建一个大小固定的线程执行者,然后修改本章第一个示例的实现。

准备工作…

你应该事先阅读本章的创建线程执行者指南,并且实现所有演示的示例,因为接下来你需要继续修改这些示例。

这个指南的例子使用Eclipse IDE实现。如果你使用Eclipse或其他IDE,如NetBeans,打开它并创建一个新的Java项目。

如何做…

按以下步骤来实现的这个例子:

1.实现本章第一个指南描述的示例,打开Server类,修改它的构造器。使用newFixedThreadPool()方法创建执行者并传入5作为参数。

1 public Server(){
2 executor=(ThreadPoolExecutor)Executors.newFixedThreadPool(5);
3 }

2.修改executeTask()方法,包含额外的日志信息行。调用getTaskCount()方法,获取已经提交给执行者的任务数。

1 System.out.printf("Server: Task Count: %d\n",executor.
2 getTaskCount());

它是如何工作的…

在本例中,你已经使用Executors类的newFixedThreadPool()方法来创建执行者。这个方法创建一个有最大线程数的执行者。如果你提交超过最大线程数的任务,剩下的任务将会被阻塞,直到有空闲的线程来处理它们。这个方法接收一个你想要让执行者拥有最大线程数的参数。在你的例子中,你已经创建了拥有5个线程的执行者。

以下截图展示了执行这个示例输出的一部分:

写入的程序输出到控制台,你已经使用了ThreadPoolExecutor类的一些方法,包括:

  • getPoolSize():此方法返回线程池实际的线程数。
  • getActiveCount():此方法返回在执行者中正在执行任务的线程数。

你可以看出这些方法的输出是5,表明执行者有5个线程。它本没有超出既定的最大线程数。

当你提交最后的任务给执行者,它只有5个活动的线程。剩下的95个任务将等待空闲线程。我们使用getTaskCount()方法来显示有多少个任务已经提交给执行者。

不止这些…

Executors类同时提供newSingleThreadExecutor()方法。这是大小固定的线程执行者的一个极端例子。它创建只有一个线程的执行者,所以它在任意时刻只能执行一个任务。

参见

  • 在第4章,线程执行者中的创建线程执行者指南
  • 在第8章,测试并发应用程序中的监控Executor framework指南
时间: 2024-08-03 18:58:55

线程执行者(三)创建一个大小固定的线程执行者的相关文章

Java基础-创建Java程序中的线程池

程序|创建 线程是Java的一大特性,它可以是给定的指令序列.给定的方法中定义的变量或者一些共享数据(类一级的变量).在Java中每个线程有自己的堆栈和程序计数器(PC),其中堆栈是用来跟踪线程的上下文(上下文是当线程执行到某处时,当前的局部变量的值),而程序计数器则用来跟踪当前线程正在执行的指令. 在通常情况下,一个线程不能访问另外一个线程的堆栈变量,而且这个线程必须处于如下状态之一: 1.排队状态(Ready),在用户创建了一个线程以后,这个线程不会立即运行.当线程中的方法start()被调

线程执行者(二)创建一个线程执行者

创建一个线程执行者 使用Executor framework的第一步就是创建一个ThreadPoolExecutor类的对象.你可以使用这个类提供的4个构造器或Executors工厂类来 创建ThreadPoolExecutor.一旦有执行者,你就可以提交Runnable或Callable对象给执行者来执行. 在这个指南中,你将会学习如何使用这两种操作来实现一个web服务器的示例,这个web服务器用来处理各种客户端请求. 准备工作 你应该事先阅读第1章中创建和运行线程的指南,了解Java中线程创

三分钟创建一个自己的移动黑客平台

本文讲的是三分钟创建一个自己的移动黑客平台, 许多朋友都希望黑客平台可以很方便的从PC移植到更便携的手机或平板电脑上,而Offensive Security团队发布的Kali NetHunter则将这一期待变为现实,通过移动终端随时随地进行黑客创意开发. Kali NetHunter是以Nexus7为基本硬件设备,基于原生Android实现的便携渗透测试平台,基于此平台,技术大咖们可以自由发挥, 创建自己的移动黑客平台 . web for pentester是国外安全研究者开发的的一款渗透测试平

线程执行者(七)执行者延迟运行一个任务

执行者延迟运行一个任务 执行者框架提供ThreadPoolExecutor类,使用池中的线程来执行Callable和Runnable任务,这样可以避免所有线程的创建操作.当你提交一个任务给执行者,会根据执行者的配置尽快执行它.在有些使用情况下,当你对尽快执行任务不感觉兴趣.你可能想要在一段时间之后执行任务或周期性地执行任务.基于这些目的,执行者框架提供 ScheduledThreadPoolExecutor类. 在这个指南中,你将学习如何创建ScheduledThreadPoolExecutor

线程-java创建一个输出流赋值为null的作用

问题描述 java创建一个输出流赋值为null的作用 public class Server { //服务端socket private ServerSocket serverSocket; //所有客户输出流 private List allOut; //线程池 private ExecutorService threadPool; /** * 构造方法,用于初始化 * / public Server() { try{ serverSocket=new ServerSocket(8088);

多线程-C++怎么在一个进程里创建一个线程

问题描述 C++怎么在一个进程里创建一个线程 大家好,我用CreateProcess创建了一个进程,进程的句柄可以获取到, 请问能否通过此句柄创建一个此进程的子线程? 如果可以,如何实现? 多谢. 解决方案 createremotethread apihttp://blog.163.com/lhc__721721/blog/static/639133252010622359175/ 解决方案二: 创建一个线程创建一个线程vc创建一个线程和销毁的方法 解决方案三: 在程序中创建另一个进程的线程,要

sqlpus 中创建一个函数打印出表空间的大小

做这个实验的目的是为了熟悉函数返回值在sqlplus中的显示,嘿嘿! 我写了个很简单的函数,在sqlpus 中操作的,偷了一下懒我用sys用户测试: 步聚如下: 1.创建一个函数 SQL> conn / as sysdba Connected. SQL> show  user; USER is "SYS" SQL> CREATE OR REPLACE FUNCTION f_tpsum(intpn IN VARCHAR2)  2  return VARCHAR2 IS

java创建线程的三种方式及其对比

Java中创建线程主要有三种方式: 一.继承Thread类创建线程类 (1)定义Thread类的子类,并重写该类的run方法,该run方法的方法体就代表了线程要完成的任务.因此把run()方法称为执行体. (2)创建Thread子类的实例,即创建了线程对象. (3)调用线程对象的start()方法来启动该线程. package com.thread; public class FirstThreadTest extends Thread{ int i = 0; //重写run方法,run方法的方

oracle创建一个数据库三步走_oracle

以前开发的时候用得比较多的是mysql和sql server,oracle用的比较少,用起来比较生疏,mysql和sql server用起来比较类似,就oracle的使用方式和他们不同,oracle在创建数据库的时候要对应一个用户,数据库和用户一般一一对应,mysql和sql server 直接通过create databse "数据库名" 就可以直接创建数据库了,而oracle创建一个数据库需要以下三个步骤: 创建两个数据库的文件 创建用户与上面创建的文件形成映射关系 给用户添加权限