相关疑难解决方法(0)

当类暴露给线程池时,清理ThreadLocal资源真的是我的工作吗?

我使用ThreadLocal

在我的Java类中,我有时会ThreadLocal主要使用一种方法来避免不必要的对象创建:

@net.jcip.annotations.ThreadSafe
public class DateSensitiveThing {

    private final Date then;

    public DateSensitiveThing(Date then) {
        this.then = then;
    }

    private static final ThreadLocal<Calendar> threadCal = new ThreadLocal<Calendar>()   {
        @Override
        protected Calendar initialValue() {
            return new GregorianCalendar();
        }
    };

    public Date doCalc(int n) {
        Calendar c = threadCal.get();
        c.setTime(this.then):
        // use n to mutate c
        return c.getTime();
    }
}
Run Code Online (Sandbox Code Playgroud)

我这样做是出于正当的原因 - GregorianCalendar是那些光荣的有状态,可变,非线程安全的对象之一,它提供跨多个调用的服务,而不是表示值.此外,它被认为是"昂贵的"实例化(这是否真实不是这个问题的重点).(总的来说,我真的很佩服它:-))

Tomcat如何发牢骚

但是,如果我在任何聚集线程的环境中使用这样的类 - 并且我的应用程序无法控制这些线程的生命周期 - 那么就有可能发生内存泄漏.Servlet环境就是一个很好的例子.

事实上,当一个webapp停止时,Tomcat 7就像这样嘶嘶作响:

严重:Web应用程序[]创建了一个ThreadLocal,其键为[org.apache.xmlbeans.impl.store.CharUtil $ 1](值[org.apache.xmlbeans.impl.store.CharUtil$1@2aace7a7])和一个值类型为[java.lang.ref.SoftReference](值[java.lang.ref.SoftReference@3d9c9ad4]),但在Web应用程序停止时无法将其删除.线程将随着时间的推移而更新,以避免可能的内存泄漏.2012年12月13日下午12:54:30 org.apache.catalina.loader.WebappClassLoader checkThreadLocalMapForLeaks

(在特定情况下,甚至我的代码都没有这样做).

谁应该受到责备? …

java concurrency thread-local threadpool

42
推荐指数
2
解决办法
2万
查看次数

如何知道Java SE类或方法是否是线程安全的?

例如:

static private DateFormat df = new SimpleDateFormat();
public static void format(final Date date) { 
   for (int i = 0; i < 10; i++) 
     new Thread(new Runnable() {
         public void run() {
             System.out.println(df.format(date));
         } 
     });
}
Run Code Online (Sandbox Code Playgroud)

DateFormat类记录为不同步类,但如果我们只使用格式方法,它不能改变整个阶级的地位?

假设它被声明为私有,如何确保代码是线程安全的?

修复此代码的最佳方法是什么?:

  1. 为每个线程使用不同的实例.

  2. 使用同步块.

java multithreading thread-safety

7
推荐指数
1
解决办法
2743
查看次数