2008-10-20 13 views
9
  1. जब जावा में कोई ऑब्जेक्ट तत्काल होता है, तो वास्तव में स्मृति में क्या चल रहा है?
  2. क्या मूल रचनाकारों की प्रतियां शामिल हैं?
  3. कास्टिंग करते समय छुपा डेटा सदस्य ओवरराइड तरीकों से अलग क्यों व्यवहार करते हैं?

मैं आम तौर पर इस सामान का सही उपयोग करने के लिए आपको बताए गए अमूर्त स्पष्टीकरण को समझता हूं, लेकिन JVM वास्तव में यह कैसे करता है।जावा इंस्टेंटेशन

उत्तर

17

जब एक वस्तु instantiated है, केवल गैर स्थिर डेटा वास्तव में "निर्मित" है, के लिए एक संदर्भ के साथ ऑब्जेक्ट का प्रकार जिसने इसे बनाया है।

कोई भी विधि कभी भी कॉपी नहीं की जाती है।

इसे बनाए गए वर्ग में "संदर्भ" वास्तव में एक सूचक प्रेषण तालिका है। वर्ग के लिए उपलब्ध प्रत्येक विधि के लिए एक सूचक मौजूद है। पॉइंटर्स हमेशा विधि के क्रियान्वयन को "सही" (आमतौर पर ऑब्जेक्ट पेड़ में सबसे कम/सबसे विशिष्ट) इंगित करते हैं।

इस तरह यदि आपके पास किसी अन्य विधि के लिए शीर्ष-स्तरीय कॉल है, लेकिन दूसरी विधि को ओवरराइड कर दिया गया है, तो ओवरराइड विधि को कॉल किया जाएगा क्योंकि वह तालिका बिंदु में पॉइंटर इंगित करता है। इस तंत्र के कारण, शीर्ष स्तर के एक से अधिक ओवरराइड विधि को कॉल करने में अधिक समय नहीं लेना चाहिए।

पॉइंटर तालिका + सदस्य चर एक वर्ग के "इंस्टेंस" हैं।

परिवर्तनीय समस्या को पूरी तरह से अलग तंत्र, "नाम रिक्त स्थान" के साथ करना है। चर सभी "उपclassed" नहीं हैं (वे प्रेषण तालिका में नहीं जाते हैं), लेकिन सार्वजनिक चर या सुरक्षित चर स्थानीय चर द्वारा छुपाया जा सकता है। यह संकलन समय पर संकलक द्वारा किया जाता है और आपके रनटाइम ऑब्जेक्ट उदाहरणों से कोई लेना-देना नहीं है। कंपाइलर निर्धारित करता है कि आप वास्तव में कौन सी ऑब्जेक्ट चाहते हैं और उसके कोड में इसका संदर्भ प्रस्तुत करते हैं।

स्कॉइंग नियम आमतौर पर "निकटतम" चर के पक्ष में हैं। किसी भी नाम से आगे कुछ भी दूर की परिभाषा के पक्ष में अनदेखा (छायांकित) किया जाएगा।

यदि आप रुचि रखते हैं तो मेमोरी आवंटन के बारे में थोड़ा और विशिष्ट प्राप्त करने के लिए: "हेप" पर असल में सभी "उद्देश्यों" आवंटित किए जाते हैं (असल में एक अद्भुत ढेर की तुलना में आश्चर्यजनक रूप से अधिक कुशल और सुंदर कुछ, लेकिन एक ही अवधारणा।) चर हमेशा पॉइंटर्स - जावा किसी ऑब्जेक्ट की प्रतिलिपि नहीं बनायेगा, आप हमेशा उस ऑब्जेक्ट पर पॉइंटर कॉपी करते हैं। विधि पैरामीटर और स्थानीय चर के लिए परिवर्तनीय पॉइंटर आवंटन स्टैक पर किए जाते हैं, लेकिन भले ही वेरिएबल (पॉइंटर) स्टैक पर बनाए जाते हैं, फिर भी वे जिन ऑब्जेक्ट्स को इंगित करते हैं वे अभी भी ढेर पर आवंटित नहीं होते हैं।

मैं एक उदाहरण लिखने के लिए प्रेरित हूं, लेकिन यह पहले से ही बहुत लंबा है। यदि आप चाहते हैं कि मैं एक विस्तार के साथ दो वर्गों को टाइप करना चाहता हूं और कैसे उनके तरीके और डेटा उत्पन्न कोड को प्रभावित करते हैं, तो मैं ... पूछ सकता हूं।

+0

क्या आप अभी भी एक उदाहरण लिखने को तैयार हैं? यदि हां, तो कृपया ऐसा करें। – Touchstone

0
  1. स्मृति सभी ऑब्जेक्ट चर और ऑब्जेक्ट और इसके सुपरस्क्लेस्स के कार्यान्वयन-विशिष्ट डेटा को पकड़ने के लिए ढेर से आवंटित किया जाता है। कार्यान्वयन-विशिष्ट डेटा में क्लाइंट और विधि डेटा के पॉइंटर्स शामिल हैं।

  2. ऑब्जेक्ट्स के आवृत्ति चर उनके डिफ़ॉल्ट मानों में प्रारंभ किए गए हैं।

  3. सबसे व्युत्पन्न कक्षा के लिए निर्माता का आह्वान किया जाता है। कन्स्ट्रक्टर द्वारा पहली चीज कन्स्ट्रक्टर को इसके अपरकेस के लिए कॉल करती है। यह प्रक्रिया तब तक जारी है जब तक java.lang.Object के कन्स्ट्रक्टर को java.lang.Object जावा में सभी ऑब्जेक्ट्स के लिए बेस क्लास नहीं कहा जाता है।

  4. कन्स्ट्रक्टर के शरीर को निष्पादित करने से पहले, सभी इंस्टेंस वैरिएबल प्रारंभकर्ता और प्रारंभिक ब्लॉक निष्पादित किए जाते हैं। तब कन्स्ट्रक्टर के व्यक्ति को निष्पादित किया जाता है। इस प्रकार, बेस क्लास के लिए कन्स्ट्रक्टर पहले पूर्ण होता है और सबसे व्युत्पन्न वर्ग के लिए कन्स्ट्रक्टर आखिरी पूरा करता है।

+0

यह सब दिलचस्प प्रकार की जानकारी है, लेकिन मुझे लगता है कि वे हिस्सों जो बिल के उत्तर से पहले से कवर नहीं हुए थे, सवाल का जवाब नहीं देते हैं। – chiccodoro

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