我必须在许多线程中并行打印许多格式化的十进制值。要格式化十进制值,我使用由模式配置的java.text.DecimalFormat
。
我知道来自DecimalFormat
的java文档的警告:
十进制格式通常不是 同步。建议 为。创建单独的格式实例 每个线程。如果有多个线程 它必须同时访问一种格式 在外部同步。
但我不知道这个警告是否适用于我的情况:
我在应用程序启动时配置java.text.DecimalFormat
一次(并将Formatter
存储在最终字段中)。之后我只使用format(double)
方法。
我之所以这样做是因为:每次我需要打印格式化的数字时,我都不希望通过创建新的DecimalFormat
实例来降低性能。
我查看了DecimalFormat.format(double)
代码,它看起来是线程安全的,但我不确定。
您是否可以确认DecimalFormat.format(double)
的使用最终是线程安全的,何时不更改格式化程序的配置,或解释为什么不是?
答案 0 :(得分:23)
只需将此线程安全代码段用于NumberFormat
:
static ThreadLocal<NumberFormat> numberFormat = new ThreadLocal<NumberFormat>() {
@Override
public NumberFormat initialValue() {
return new DecimalFormat("00000");
}
};
或者在Java 8中,正如Jesper在评论中所说:
private static ThreadLocal<NumberFormat> numberFormatter =
ThreadLocal.withInitial(() -> new DecimalFormat("00000"));
答案 1 :(得分:20)
虽然当前的实现可能最终是线程安全的,但是对于即将到来的实现或其他JRE没有这样的保证。
您是否确认避免new DecimalFormat()
在您的申请中获得可衡量的效果?
答案 2 :(得分:6)
如果不在此实例上调用其他方法,则DecimalFormat的当前Hotspot实现将调用DecimalFormat.format(double)线程安全。但是强烈建议不要依赖这种(可能)临时行为。
您是否考虑使用ThreadLocal
变量来避免过多new DecimalFormat()
?