2013-01-24 16 views
9

जावा में कचरा संग्रह एक ऑब्जेक्ट एक्स पर अंतिम विधि का आह्वान करेगा यदि एक्स और एक्स को इंगित करने वाला कोई मजबूत संदर्भ कचरा संग्रह के लिए योग्य नहीं है। क्या होगा यदि अंतिम विधि कभी समाप्त नहीं होती है, तो क्या यह स्मृति रिसाव का कारण बनता है?जावा: बीमार मेमोरी लीक बनाने के लिए बीमार परिभाषित विधि

 
public class X{ 
    protected void finalize(){ 
    while(true){} 
    } 
} 
+7

क्या आपको यह कोशिश करने से रोकता है? वास्तव में इसे आजमाने के लिए –

उत्तर

2

हां।
यदि आप ऑब्जेक्ट को अंतिम रूप देने के लिए ऑब्जेक्ट के वैध संदर्भ देते हैं, तो विधि को अंतिम रूप देने के अंदर, जावा ऑब्जेक्ट को कचरा नहीं करेगा, फिर भी अंतिम बार फिर से लागू नहीं किया जाएगा क्योंकि इसे केवल एक बार बुलाया जाता है।

2

निश्चित रूप से। विधि को वापस करने के बाद स्मृति को हटा दिया जाएगा। और यदि आपका अंतिम रूप कभी वापस नहीं आता है, तो मोमबत्ती को हटाया नहीं जाएगा।

कचरा संग्रहण में जी उठने के बारे में

गूगल और आप

6

हाँ, यह आसान

public class X { 

    protected void finalize() { 
     while (true) { 
     } 
    } 

    public static void main(String[] args) throws Exception { 
     while (true) { 
      new X(); 
     } 
    } 
} 

कुछ समय मैं

मिला के बाद परीक्षण करने के लिए होगा विभिन्न मामलों में जहां को अंतिम रूप देने विधि जीसी की गारंटी नहीं है मिल जाएगा
Exception: java.lang.OutOfMemoryError thrown from the UncaughtExceptionHandler in thread "main" 

जब मैंने अंतिम रूप दिया() परीक्षण कभी नहीं रुक गया। ध्यान दें कि यह कुछ समय लगता है इससे पहले कि JVM OOM चला जाता है

BTW यह इस परीक्षण

public class X { 
    byte[] a = new byte[100 * 1000 * 1000]; 

    protected void finalize() { 
     System.out.println(); 
    } 

    public static void main(String[] args) throws Exception { 
     while (true) { 
      new X(); 
     } 
    } 
} 

जीसी बाहर तोड़

Exception in thread "main" 
java.lang.OutOfMemoryError: Java heap space 
    at test.X.<init>(X.java:5) 
    at test.X.main(X.java:13) 

टिप्पणी //System.out.println चलाने के लिए पर्याप्त है (); और यह गैर-स्टॉप

+1

+1! =) – pcalcao

+0

दिलचस्प बात यह है कि मैक ओएस एक्स पर, प्रोग्राम सिर्फ त्रुटि संदेश के साथ समाप्त हो जाता है। मैंने थोड़ी देर के दौरान अपवाद हैंडलिंग जोड़ा, लेकिन कोई अपवाद नहीं पकड़ा गया। मैंने अंतिम रूप से कुछ आउटपुट भी जोड़ा, यह देखने के लिए कि क्या इसे कभी भी बुलाया गया था, लेकिन कोई भी दिखाया नहीं गया था। – Henrik

+0

ओह, आप कभी नहीं जानते, मेरे जवाब को "हां, यह हो सकता है ..." –

0

यह java.lang.ref.Finalizer $ FinalizerThread (The Secret Life Of The Finalizer) को अवरुद्ध करेगा, अंतिम विधि लागू करने वाले सभी वर्गों का उदाहरण java.lang.ref.Finalizer.ReferenceQueue में अवरुद्ध किया जाएगा। आप 'अंतिमकरण' के साथ नई वस्तु बनाते रहेंगे, उन वस्तुओं द्वारा स्मृति समाप्त हो जाएगी जो अंतिम रूप देने के लिए प्रतीक्षा कर रहे हैं। यदि एक ढेर डंप लें, तो आप देखेंगे कि वस्तुओं को java.lang.ref.Finalizer द्वारा बनाए रखा गया है, उदाहरण के नीचे देखें (यह एक वास्तविक मामला है)। enter image description here

संबंधित मुद्दे