inheritance in c++ what



सी++: खाली वर्ग की वस्तु का आकार क्या है? (11)

एक अपवाद है: 0-लंबाई सरणी

#include <iostream>

class CompletlyEmpty {
  char NO_DATA[0];
};

int main(int argc, const char** argv) {
  std::cout << sizeof(CompletlyEmpty) << '\n';
}

https://ffff65535.com

मैं सोच रहा था कि खाली वर्ग की वस्तु का आकार क्या हो सकता है। यह निश्चित रूप से 0 बाइट्स नहीं हो सकता है क्योंकि इसे किसी अन्य ऑब्जेक्ट की तरह संदर्भित करना और इंगित करना संभव होना चाहिए। लेकिन, ऐसी वस्तु कितनी बड़ी है?

मैंने इस छोटे कार्यक्रम का इस्तेमाल किया:

#include <iostream>
using namespace std;

class Empty {};

int main()
{
    Empty e;
    cerr << sizeof(e) << endl;
    return 0;
}

विजुअल सी ++ और सिग्विन-जी ++ कंपाइलर्स दोनों में जो आउटपुट मिला, वह 1 बाइट था! यह मेरे लिए थोड़ा आश्चर्यजनक था क्योंकि मुझे यह उम्मीद थी कि यह मशीन शब्द (32 बिट्स या 4 बाइट्स) के आकार का होगा।

क्या कोई बता सकता है कि 1 बाइट का आकार क्यों ? 4 बाइट क्यों नहीं ? क्या यह संकलक या मशीन पर भी निर्भर है? साथ ही, क्या कोई खाली कोड ऑब्जेक्ट 0 बाइट्स का आकार क्यों नहीं ले सकता है?


एक खाली कक्षा के लिए 1 बाइट आवंटन संकलक निर्भर है। कंपाइलर्स को यह सुनिश्चित करने की ज़रूरत है कि ऑब्जेक्ट्स अलग-अलग मेमोरी स्थानों में रहें और उन्हें ऑब्जेक्ट में शून्य शून्य मेमोरी आकार आवंटित करने की आवश्यकता है। इस विषय पर नोट्स सुनें: http://listenvoice.com/listenVoiceNote.aspx?id=27

यद्यपि संकलक गैर शून्य आकार को खाली कक्षा में आवंटित करते हैं, फिर भी वे खाली कक्षाओं से नई कक्षाएं प्राप्त होने पर अनुकूलन भी करते हैं। सुनोवॉइस के सी ++ प्रोग्रामिंग साक्षात्कार के प्रश्नों पर खाली आधार अनुकूलन के बारे में सुनो।


बिना डेटा सदस्यों वाले कक्षा के कारण, लेकिन आकार 1 बाइट होने का कारण यह है कि यह * मजबूत पाठ * स्मृति में संग्रहीत किया जाना चाहिए ताकि संदर्भ या सूचक उस वर्ग के ऑब्जेक्ट को इंगित कर सके


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


मुझे लगता है कि अगर खाली वर्ग का आकार शून्य है तो इसका मतलब है कि यह अस्तित्व में नहीं है। इसके लिए (वर्ग) मौजूद है, इसके लिए कम से कम 1 बाइट होना आवश्यक है, क्योंकि यह बाइट स्मृति / संदर्भ पता है।


मुझे लगता है कि ऐसा इसलिए है क्योंकि 1 बाइट छोटी स्मृति इकाई है जिसे प्लेसहोल्डर के रूप में उपयोग किया जा सकता है, और यह शून्य आकार नहीं दे सकता क्योंकि ऑब्जेक्ट्स की सरणी बनाना संभव नहीं होगा ..

और जो चीज आपने कहा था "यह मेरे लिए थोड़ा आश्चर्यजनक था क्योंकि मैं इसे मशीन शब्द (32 बिट्स या 4 बाइट्स) के आकार के होने की उम्मीद कर रहा था।" रिक्त () के संदर्भ चर (मैकिन शब्द) के लिए सत्य होगा (), वर्ग के आकार का नहीं (जो सार डेटा प्रकार है)


मुझे लगता है कि यह भी अच्छा जवाब देने के उत्तर से लिंक करना उपयोगी हो सकता है। यह लोगान कैपल्दो द्वारा boost::compressed_pair बारे में है।


यह इस सूचक के कारण है, यद्यपि सूचक 4 बाइट का (पूर्णांक) है लेकिन यह एक स्मृति स्थान (एक इकाई) का संदर्भ देता है जो 1 बाइट है।


यह वास्तव में एक कार्यान्वयन विस्तार है। एक बार बहुत पहले, मैंने सोचा था कि यह शून्य बाइट्स या एक हजार बाइट्स हो सकता है, इसका भाषा विनिर्देश पर कोई असर नहीं पड़ता है। लेकिन, मानक (धारा 5.3.3) को देखने के बाद, sizeof को हमेशा एक या अधिक लौटने के रूप में परिभाषित किया जाता है, इससे कोई फर्क नहीं पड़ता।

सबसे व्युत्पन्न वर्ग का आकार शून्य से अधिक होगा।

यह अन्य चीजों के साथ, आपको ऑब्जेक्ट्स और पॉइंटर्स के सरणी को संभालने की इजाजत देता है। यदि आपके तत्वों को शून्य आकार के होने की अनुमति दी गई थी &(array[0]) समान &(array[42]) समान होगी, जो आपके प्रसंस्करण loops के सभी प्रकार के विनाश का कारण बन जाएगी।

इसका कारण यह है कि यह मशीन शब्द नहीं हो सकता है कि इसमें कोई तत्व नहीं है जिसके लिए वास्तव में इसे शब्द सीमा (जैसे एक पूर्णांक) पर गठबंधन करने की आवश्यकता होती है। उदाहरण के लिए, यदि आप char x; int y; char x; int y; कक्षा के अंदर, मेरा जीसीसी आठ बाइट्स पर घूमता है (क्योंकि दूसरे int को उस कार्यान्वयन में गठबंधन किया जाना चाहिए)।


यह सुनिश्चित करने के लिए nonzero है कि दो अलग-अलग वस्तुओं के अलग-अलग पते होंगे। अलग-अलग वस्तुओं में अलग-अलग पते होना चाहिए, इसलिए खाली कक्षा का आकार हमेशा 1 बाइट होता है।


#include<iostream>
using namespace std;


    class Empty { };
    int main()
    {
        Empty* e1 = new Empty;
        Empty* e2 = new Empty;

        if (e1 == e2)
            cout << "Alas same address of two objects" << endl;
        else
            cout << "Okay it's Fine to have different addresses" << endl;

        return 0;
    }

आउटपुट: ठीक है, यह अलग-अलग पते के लिए ठीक है

रिटर्निंग आकार 1 सुनिश्चित करता है कि दोनों ऑब्जेक्ट्स का एक ही पता नहीं होगा।





object