Oncelikler benim bildiğin threadLocal tanımını yapayım.ThreadLocal kendisine generic olarak verilen veri tipi için cağıran tüm thread ler için yeni bi instance dündürür.Peki kanallar arasında ortak kullanılan nesneleri her sınıfta tanımlamak yerine neden ThreadLocal den cekiyoruz? ThreadLocal de yeni bi instance olusturuyor bellek acısından değişen bi nokta yok gibi. Ayrıca threadlocalde initial olarak bir A nesnesi olduğunu düşünelim.A nesnesini bir kanal elde edip üzerinde değişiklik yaptktan sonra 2. bir kanal A nesnesinin hangi instance ına erişicektir ilk haldekimi değişmiş olan mı? threadlocal ın remove metodu nun çağrılmamasının bazı riskler doğuracağı yazıyor(bellek,güvenlik sıkıntıları gibi)bunun nasıl olabileceğini bir senaryo ile acıklayabilirmisiniz lütfen.

soruldu: 23 Ara '12, 09:04

Sheriff's gravatar image

Sheriff
12691116
cevap kabul oranı: 28%

değiştirildi: 24 Ara '12, 01:01

%C3%B6zcanacar's gravatar image

özcanacar ♦♦
17.2k59183183


ThreadLocal kendisine generic olarak verilen veri tipi için cağıran tüm thread ler için yeni bi instance dündürür

Bu tanımdaki hata şu, Thread'ler için yeni bir instance yaratıp döndürmez, ThreadLocal nesnesine erişen thread'in daha önceden set etmiş olduğu nesneyi döndürür.Bu thread daha önceden nesne set etmemişse, ThreadLocal nesnesi initialValue metodunu çağırarak set eder ve o nesneyi döner.

public static final ThreadLocal<SimpleDateFormat> shared = 
        new ThreadLocal <SimpleDateFormat> () {
            @Override 
            protected SimpleDateFormat initialValue() {
                return new SimpleDateFormat("dd.MM.yyyy HH:mm.ss.SSS z");
        } 
};

Bu şekilde oluşturulan shared nesnesine T1, T2 thread'lerinden erişilsin diyelim.

T1'de shared.get() çağrıldığında T1 daha önce herhangi bir şey set etmediği için shared.get() kendi içinde initialValue() metodunu çağırır. initialValue() metodunu yukarıda biz override etmiştik. Bu yüzden yeni bir SimpleDateFormat nesnesi yaratılır ve dönülür. T1 tekrar shared.get() metodunu çağırırsa önceden yaratılan nesne dönülür, yeni nesne yaratılmaz.

Yukarıdakiler olduktan sonra, T2 shared.get() metodunu çağırırsa, T2 önceden bir şey set etmediği için yeni SimpleDateFormat nesnesi yaratılır ve dönülür. T1'in set ettiği nesneyi T2 göremez.

Anlamlı olmasa da, uygulamak için aşağıdaki kod kullanılabilir.

public class Demo {

    private static final ThreadLocal<String> shared = 
        new ThreadLocal <String> () {
            @Override 
            protected String initialValue() {
                return Thread.currentThread().getName();
        }
    };

    public static void main(String[] args) {
        Thread t1 = new Demo.SimpleThread();
        Thread t2 = new Demo.SimpleThread();
        Thread t3 = new Demo.SimpleThread();

        t1.start();
        t2.start();
        t3.start();
    }

    static class SimpleThread extends Thread{
        @Override
        public void run(){
            System.out.println(shared.get());
        }
    }
}

Daha düzgün anlatım için buralara bakılabilir.

http://docs.oracle.com/javase/6/docs/api/java/lang/ThreadLocal.html
http://java.dzone.com/articles/java-thread-local-%E2%80%93-how-use
http://javapapers.com/core-java/threadlocal/
permanent link

cevaplandı: 26 Ara '12, 10:16

Mesut's gravatar image

Mesut
60721017
cevap kabul oranı: 25%

1

Anlatım için teşekkürler.Peki t1 thread i sdf nesnesini kullandıktan sonra shared.set(null) seklinde bir atama yapmazsa eger hangi senaryoda bi açık olusabilir?

(27 Ara '12, 13:51) Sheriff Sheriff's gravatar image

Sdf nesnesinin ömrü T1'e bağımlı. T1 sonlandığında, T1 ve sdf garbage collector ile temizlenebilir durumda olur. Özellikle null atamaya gerek kalmaz. Sorun olabilecek duruma örnek olarak şu olabilir. Yazdığımız uygulama Java EE uygulama sunucusunda çalışıyorsa, çok yüksek ihtimal thread havuzu vardır. Yani server thread'in işi bittiğinde thread'i sonlandırmayıp havuza geri döndürür. Thread sonlanmadığı için bu thread'e bağımlı ThreadLocal nesneleri temizlenemez. Bu yüzden memory leak oluşur, belki de uygulamada bug'a yol açar.

(28 Ara '12, 09:31) Mesut Mesut's gravatar image
Cevabınız
toggle preview

Bu soruyu takip et

E-Posta üzerinden:

Üyelik girişi yaptıktan sonra abonelik işlemlerini yapabilirsiniz

RSS üzerinden:

Cevaplar

Cevaplar ve Yorumlar

Yazı Formatlama

  • *italic* ya da _italic_
  • **bold** ya da __bold__
  • link:[text](http://url.com/ "başlık")
  • resim?![alt text](/path/img.jpg "başlık")
  • liste: 1. Foo 2. Bar
  • temel HTML etiketleri de kullanılabilir

Bu sorunun etiketleri:

×31

Soruldu: 23 Ara '12, 09:04

Görüntüleme: 993 kez

Son güncelleme: 28 Ara '12, 09:31

powered by BitNami OSQA