28

Java 中的无状态 bean 不会在来自客户端的两次调用之间保持其状态。所以简而言之,我们可以将它们视为具有业务方法的对象。每个方法都接受参数并返回结果。当调用该方法时,正在执行堆栈中创建一些局部变量。当方法返回时,从堆栈中删除局部变量,如果分配了一些临时对象,它们无论如何都会被垃圾回收。

从我的角度来看,这与通过单独的线程调用同一单个实例的方法没有什么不同。那么,为什么一个容器不能使用一个 bean 的实例而不是汇集多个实例呢?

4

5 回答 5

29

池化做了几件事。

一,通过每个实例有一个bean,可以保证线程安全(例如,Servlet 不是线程安全的)。

第二,您减少了 bean 可能具有的任何潜在启动时间。虽然会话 Bean 是“无状态的”,但它们只需要对客户端是无状态的。例如,在 EJB 中,您可以将多个服务器资源注入到一个会话 Bean 中。该状态对于 bean 来说是私有的,但是没有理由不能阻止它从调用到调用。因此,通过合并 bean,您可以将这些查找减少到仅在创建 bean 时发生。

三、可以使用 bean pool 作为限制流量的手段。如果池中只有 10 个 Bean,则最多只能有 10 个请求同时工作,其余的将排队。

于 2008-09-25T18:24:22.357 回答
1

池化提高了性能。

处理所有请求/线程的单个实例会导致大量争用和阻塞。

由于您不知道将使用哪个实例(并且多个线程可以同时使用一个实例),因此 bean 必须是线程安全的。

容器可以根据实际活动管理池大小。

于 2008-09-25T20:30:17.047 回答
1

Java EE 模型的事务性使用线程上下文来管理事务生命周期。

存在这种简化,因此无需实现任何特定接口即可直接与 UserTransaction 对象交互;当从 InitialContext 检索事务(或注入会话 bean)时,它被绑定到线程局部变量以供重用(例如,如果无状态会话 bean 中的方法调用另一个也使用注入事务的无状态会话 bean。 )

于 2008-10-30T20:26:05.060 回答
0

Statelesss会话bean的生命周期是不存在,Passive和MethodReady(Passive或Inactive)状态。为了优化性能,而不是从创建到方法就绪状态遍历bean,容器通过管理主动和被动状态之间的bean容器回调 - ejbActivate() 和 ejbPassivate() 通过管理 bean 池。

sreenut

于 2008-09-25T19:13:38.820 回答
0

方法本质上是线程安全的(包括静态的)。为什么?很简单,因为方法中的每个变量都是在堆栈内存中创建的,即方法中使用的每个变量都是每次调用创建的(它不是共享的)。但是,参数不是堆栈的一部分。

但是,如果方法使用不安全的变量,则该方法是不安全的:

a) 调用静态字段或变量。然而,它发生在每一种情况下。

b) 调用它共享的资源。比如EntityManager。

c) 传递一个不安全的参数。

于 2018-03-30T13:23:20.697 回答