java - 使用静态初始化 block 来提高性能

标签 java performance static-initialization

假设生产中使用的现有代码库包含一个类 A,该类包含一个使用 setter 填充另一个 POJO 类 B 的 N 个字段并将 POJO 返回给调用者的方法,并且假设类 B 的所有实例在仅考虑两个字段,即 N - 2 个字段在 B 类的所有实例中都是相同的,如果 A 类具有对 B 类的静态引用并初始化不更改的 B 类字段,是否会有任何性能增益在静态初始化 block 中?这样,每次调用时填充类 B 的 N 个字段的类 A 中的方法现在只需填充两个不同的字段。这也将消除为每次调用类 A 中的方法创建类型 B 的新对象的需要。这种方法在多线程应用程序中有何含义?

或者,我们可以将类 B 中所有不更改的字段声明为静态,以便类 A 中的方法仅设置每次调用时更改的字段。无论哪种方式,性能提升是否值得,或者这种变化是否属于过早优化?

示例:

class A { 
     private static B b = new B(); 

     static {
         b.setSystem("MySystem");
         b.setVersion("1.1");
     }

     public B getB(String name) {
         b.setName(name);
         return B;

     }
}

最佳答案

given that all instances of class B will be different in regards to only two field

所以我知道您有多个 B 实例

This will also eliminate the need to create a new object of type B for each call to the method in class A.

但现在您只有一个 B 实例 - 如果 A 更改这 2 个字段,则代码中引用该 B 实例的所有位置都将看到更改(假设同步正确)。

=> 尚不清楚您是否需要一个或多个 B 实例。

What are the implications of this approach in a multi-threaded application?

如果跨线程共享 B 的同一个实例,则需要确保在写入和读取 B 的属性时使用正确的同步。

Alternately, we can declare all the fields in class B that don't change as static

你的意思是最终的吗?

Either ways, will the performance gain be worth it or this change qualifies as premature optimization?

它认为它确实符合条件。特别是因为您似乎还不能 100% 确定自己需要什么。所以和往常一样的建议是:走简单的路。 如果性能不够好,分析并确定代码的哪些部分需要改进。

如果您知道自己将处于多线程环境中,那么您可能应该避免任何静态和可变的东西 - 这将使您的生活更轻松并限制并发错误的风险。

理想情况下,(1) 尽量不要跨线程共享对象 - 如果不能,则 (2) 尝试共享不可变对象(immutable对象) - 如果不能 (3) 确保使用正确的同步,并且知道你在做什么。

关于java - 使用静态初始化 block 来提高性能,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12277991/

相关文章:

java - 实例化 Map 时使用 Wrapper 类作为键和值

java - JAVA中查找子字符串的最快方法

html - 修复了在 html 表格标题处滚动而不影响标题大小

java - Initialize-On-Demand 习语与单例实现中的简单静态初始化程序

c++ - std::set 用作静态模板化成员变量

java - 用于 Android 的通用图像加载器,在 Fragment 中带有 ImageView

java - 使用 jooq 通过子查询删除

python - 在 4 个 CPU 上执行 CPU 绑定(bind)任务时,20 个进程中的 400 个线程优于 4 个进程中的 400 个线程

c++ - 是否可以确保仅在 'static initialization' 步骤期间调用函数

java - 如何使用 AsyncHttpClient 对错误的 http 代码实现重试功能?