2012-04-24 9 views
5

मैं फिर एक वर्ग मदक्या यह वस्तु का एक सुरक्षित प्रकाशन है?

class Item { 
    public int count; 
    public Item(int count) { 
    this.count = count; 
    } 
} 

है, मैं अन्य वर्ग

class Holder { 
    public Item item; 
    public Holder() { 
    item = new Item(50); 
    } 
} 

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

+0

विषय पर दिलचस्प DW लेख कि तुल्यकालन से संबंधित मुद्दों के कई की पड़ताल: http://www.ibm.com/developerworks/java/library/j-jtp0618/index.html – maksimov

+0

मैं बहुत माफी चाहता हूँ, मैं इसे भूल गए हैं! – ohyeahchenzai

उत्तर

13

क्या यह नया आइटम ऑब्जेक्ट सुरक्षित रूप से प्रकाशित किया जा सकता है? यदि नहीं, क्यों?

समस्या अनुकूलन के आसपास घूमती है और निर्देशों के पुनरीक्षण के आसपास घूमती है। आप दो धागे कि तुल्यकालन के बिना एक निर्माण वस्तु का उपयोग कर रहे होते हैं, तो यह हो सकता है कि संकलक दक्षता खातिर निर्देश को पुन: व्यवस्थित और एक वस्तु के लिए स्मृति स्थान का आवंटन और इसके समाप्त होने से पहले item क्षेत्र में अपनी संदर्भ स्टोर करने के लिए फैसला करता है कन्स्ट्रक्टर और फील्ड प्रारंभिक के साथ। या यह स्मृति सिंक्रनाइज़ेशन को पुन: व्यवस्थित कर सकता है ताकि अन्य धागे इस तरह से समझ सकें।

यदि आप item फ़ील्ड को final के रूप में चिह्नित करते हैं तो कन्स्ट्रक्टर को उस क्षेत्र के प्रारंभकर्ता को कन्स्ट्रक्टर के हिस्से के रूप में प्रारंभ करने की गारंटी दी जाती है। अन्यथा इसका उपयोग करने से पहले आपको लॉक पर सिंक्रनाइज़ करना होगा। यह Java language definition का हिस्सा है।

यहाँ एक और जोड़ी के संदर्भ दिया गया है:

+0

शायद मुझे जावा भाषा विनिर्देश पढ़ना चाहिए, धन्यवाद! – ohyeahchenzai

+0

मुझे आपको सीधे [अध्याय।] (Http://docs.oracle.com/javase/specs/jls/se7/html/jls-17.html#jls-17.4) पर इंगित करने दें, यह एक बहुत अच्छा पढ़ा है, बहुत कुछ सूखे विनिर्देश से अधिक। –

+0

धन्यवाद @ मार्को। मैंने उस लिंक को मेरे उत्तर में जोड़ा है। – Gray

5

हाँ, वहाँ, एक दृश्यता समस्या यह है के रूप में Holder.itemfinal नहीं है। तो इस बात की कोई गारंटी नहीं है कि Holder के निर्माण के बाद एक और धागा अपना प्रारंभिक मूल्य देखेगा।

और जैसा कि @Gray ने कहा, JVM() जिसमें लॉक (तुल्यकालन द्वारा बनाया जा सकता है, एक final या volatile क्वालीफायर) स्मृति बाधाओं के अभाव में निर्देश को पुन: व्यवस्थित करने के लिए स्वतंत्र है। संदर्भ के आधार पर, आपको सुरक्षित प्रकाशन सुनिश्चित करने के लिए इनमें से एक का उपयोग करना होगा।

+0

मुझे लगता है कि मुझे जवाब मिल सकता है, यह पुनरावृत्ति है, लेकिन मुझे यह बिल्कुल सही आदेश नहीं है, लेकिन ग्रे ने इसे इंगित किया है, मुझे इसके बारे में कुछ पता है, धन्यवाद! – ohyeahchenzai

+0

@ohyeahchenzai अगर आप ध्यान से अध्याय का अध्ययन करते हैं तो जेएलएस ने दूसरे उत्तर में उल्लेख किया है, तो यह सब आपको स्पष्ट होगा। –

+0

फ़ील्ड को अंतिम बनाकर अपरिवर्तनीयता का पक्ष लेने का एक और अच्छा कारण है। –

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