Java EE 7 并发编程Concurrency UtilitiesWord文档格式.docx
《Java EE 7 并发编程Concurrency UtilitiesWord文档格式.docx》由会员分享,可在线阅读,更多相关《Java EE 7 并发编程Concurrency UtilitiesWord文档格式.docx(8页珍藏版)》请在冰豆网上搜索。
我们可以清楚的看到应用程序idea.exe持有71个线程,而其他的应用程序则使用了较少的线程。
因此,如果我有5000个任务并且为这5000个任务创建了5000个不同的线程,这难道意味着我设计了一个好的架构吗?
(当然不是)
事实上,如果我把这5000个任务按照一定规则(随机分配或按优先级分配)安排在特定数量的工作线程上运行,会更高效地利用系统资源而且不会给系统带来不必要的压力。
由于上面的图中设定了5个工作线程,这5000个任务在操作系统看来最多只有5个用户自定义任务在运行。
当一个工作线程执行结束后,会从当前处于等待状态的任务中选取一个执行,这个过程会持续进行直到所有的任务都执行完成。
因此,Java
SE
1.5版本推出的Executor
API的基本原理是通过提供多种线程池环境实现高效的线程管理。
工作线程是线程工厂生产的通用线程。
ExecutorService和ScheduledExecutorService是Executor
API中的基本接口。
这些接口的实现可能是Executors类的一系列静态方法。
Java
EE
7版本推出的新Concurrency
Utilities标准通过容器服务提供这些对象的注入和管理。
容器管理的Executor对象以XXXExecutorService和XXXScheduledExecutorService的形式命名,如ManagedExecutorService和ManagedScheduledExecutorService标识了它是可管理的。
你可以查看这些接口的UML图,了解Java
Executor
API接口间的继承关系。
以“Managed”开头的接口基本上和Java
API组件提供相同的操作。
不同之处在于,其创建的对象将以容器资源(container
resources)的形式提供给开发者。
容器资源是由应用服务器管理的特殊对象。
DataSources、JMS
resources以及Concurrency
Utilities中的Concurrency
units都属于容器资源。
容器资源是驻留在应用服务器上并提供特定功能的对象。
这些对象可以通过JNDI(Java
Naming
and
Directory
Interfaces)标准进行访问。
@Resource注解和Context接口类型的对象(如:
InitialContext)基本上可以实现对这些对象的访问。
创建并发资源
支持Java
7版本的应用服务器能够创建Concurrency
Utilities中可管理的Executor对象。
例如,这个创建过程可以通过Glassfish
4的asadmin命令集或者Glassfish管理员控制台直观地定义出来。
Glassfish应用服务器/bin目录下的asadmin
tool用于命令行操作。
下面的例子使用了asadmin
tool,并通过create-managed-executor-service
命令和create-managed-scheduled-executor-service命令创建可管理的Executor对象。
因为容器资源在被提供给应用环境时携带着遵从JNDI标准定义的访问表达式,所以需要在控制台中输入代表该容器资源的唯一访问标识符。
在Glassfish管理员控制台中能够看到可管理的Executor对象。
与此同时,在管理员控制台中也能够进行添加和修改。
Glassfish
4的容器资源显示在控制台的Resources标签下。
并发资源显示在子标签Concurrent
Resources下。
而我们创建的用于容器管理的ManagedExecutorService和ScheduledManagedExecutorService
资源就能在这个子标签下找到。
由应用服务器内部定义的带__default前缀的并发资源也是可用的。
如果需要的话,也可以使用现有的默认资源。
获取Concurrency
Utilities中的资源
注入的@Resource注解和InitialContext对象能够访问驻留在应用服务器上的并发资源。
@Resource注解和InitialContext对象提供标准的JNDI访问不仅适用于并发资源,还适用于其他容器资源。
1
@WebServlet(urlPatterns=
"
/kodcu"
name=
KodcuServlet"
)
2
public
class
KodcuServlet
extends
HttpServlet{
3
4
@Resource
//
(1)
5
private
ManagedExecutorServicedefaultmanagedExecutorService;
6
7
//
(2)
8
ManagedScheduledExecutorServicedefaultScheduledExecutorService;
9
10
@Resource(lookup=
concurrent/KodcuExecutor"
)
//(3)
11
ManagedExecutorServicemanagedExecutorService;
12
13
concurrent/KodcuScheduledExecutor"
//(4)
14
ManagedScheduledExecutorServicescheduledExecutorService;
15
16
@Override
17
protected
void
doGet(HttpServletRequestreq,HttpServletResponseresp)throws
ServletException,IOException{
18
19
...
20
21
InitialContextcontext=new
InitialContext();
//(5)
22
23
ManagedExecutorServicemanagedExecutorServiceWithContext=(ManagedExecutorService)context.lookup("
);
24
25
26
27
}
28
29
上面的Servlet类,使用@Resource注解获取默认的并发资源(编号1和编号2)以及在命令行中指定特定JNDI名称所创建的并发资源(编号3和编号4)。
@Resource注解的lookup字段存放着相应对象的唯一资源访问标识符,该标识符遵从JNDI标准。
当@Resource注解没有设定lookup字段时,注入的是带有__default前缀的默认JNDI资源。
除了使用注解的方法之外,在编号5的代码段中,使用InitialContext对象根据JNDI名称获取相应的并发资源。