Bool प्रकार भाषा runtimes के बीच कई असंगत विकल्पों के साथ एक चेकर इतिहास रहा है। यह डेनिस रिची द्वारा बनाए गए ऐतिहासिक डिजाइन-विकल्प के साथ शुरू हुआ, जिस आदमी ने सी भाषा का आविष्कार किया था। यह एक नहीं था bool प्रकार, विकल्प था पूर्णांक जहां 0 से मूल्य का प्रतिनिधित्व करता झूठी और किसी भी अन्य मूल्य माना जाता था सच ।
इस पसंद को Winapi में आगे बढ़ाया गया था, जो पिनवोक का उपयोग करने का प्राथमिक कारण है, इसमें एक टाइफाइड है BOOL
जिसके लिए सी कंपाइलर के इंट कीवर्ड के लिए एक उपनाम है । यदि आप एक स्पष्ट [मार्शल] विशेषता को लागू नहीं करते हैं, तो एक C # बूल एक BOOL में परिवर्तित हो जाता है, इस प्रकार एक क्षेत्र का निर्माण होता है जो 4 बाइट लंबा होता है।
आप जो भी करते हैं, आपकी संरचना की घोषणा के लिए आपके द्वारा इंटरॉप की गई भाषा में रनटाइम पसंद के साथ एक मैच होना चाहिए। जैसा कि नोट किया गया है, winapi के लिए BOOL लेकिन अधिकांश C ++ कार्यान्वयन ने बाइट को चुना , अधिकांश COM स्वचालन इंटरॉप VARIANT_BOOL का उपयोग करता है जो कि एक छोटा है ।
वास्तविक एक सी # का आकार bool
एक बाइट है। सीएलआर का एक मजबूत डिजाइन-लक्ष्य यह है कि आप इसका पता नहीं लगा सकते हैं। लेआउट एक कार्यान्वयन विवरण है जो प्रोसेसर पर बहुत अधिक निर्भर करता है। वैरिएबल प्रकार और संरेखण के बारे में प्रोसेसर बहुत अशिष्ट हैं, गलत विकल्प प्रदर्शन को काफी प्रभावित कर सकते हैं और रनटाइम त्रुटियों का कारण बन सकते हैं। लेआउट को अनदेखा करके, .NET एक सार्वभौमिक प्रकार प्रणाली प्रदान कर सकता है जो वास्तविक रनटाइम कार्यान्वयन पर निर्भर नहीं करता है।
दूसरे शब्दों में, आपको हमेशा लेआउट को बंद करने के लिए रनटाइम पर एक संरचना को मार्शल करना होगा। जिस समय आंतरिक लेआउट से इंटरोप लेआउट में रूपांतरण किया जाता है। यह बहुत तेज़ हो सकता है यदि लेआउट समान है, धीमा है जब खेतों को फिर से व्यवस्थित करने की आवश्यकता होती है क्योंकि हमेशा संरचना की एक प्रति बनाने की आवश्यकता होती है। इसके लिए तकनीकी शब्द ब्लिटेबल है , देशी कोड के लिए एक सम्मोहक संरचना पास करना तेज़ है क्योंकि पिनवोक मार्शेलर केवल एक पॉइंटर पास कर सकता है।
प्रदर्शन भी मूल कारण है कि एक बूल एक बिट नहीं है। कुछ प्रोसेसर हैं जो सीधे सीधे पता करने योग्य बनाते हैं, सबसे छोटी इकाई एक बाइट है। एक अतिरिक्त निर्देश को बाइट से मछली को निकालने की आवश्यकता होती है, जो मुफ्त में नहीं आती है। और यह कभी भी परमाणु नहीं है।
C # संकलक अन्यथा आपको यह बताने में संकोच नहीं करता है कि यह 1 बाइट लेता है, उपयोग करें sizeof(bool)
। यह अभी भी एक शानदार भविष्यवक्ता नहीं है कि कितने बाइट्स किसी क्षेत्र को रनटाइम पर लेते हैं, सीएलआर को .NET मेमोरी मॉडल को लागू करने की भी आवश्यकता होती है और यह वादा करता है कि सरल चर अपडेट परमाणु हैं । इसके लिए चर को ठीक से मेमोरी में संरेखित करने की आवश्यकता होती है ताकि प्रोसेसर इसे एकल मेमोरी-बस चक्र के साथ अपडेट कर सके। बहुत बार, एक बूल को वास्तव में इसकी वजह से स्मृति में 4 या 8 बाइट्स की आवश्यकता होती है। अतिरिक्त गद्दी जो यह सुनिश्चित करने के लिए जोड़ी गई थी कि अगला सदस्य ठीक से संरेखित हो।
सीएलआर वास्तव में लेआउट के अनदेखे होने का फायदा उठाता है, यह एक वर्ग के लेआउट का अनुकूलन कर सकता है और खेतों को फिर से व्यवस्थित कर सकता है ताकि पैडिंग कम से कम हो। तो, कहते हैं, यदि आपके पास बूल + इंट + बूल सदस्य के साथ एक वर्ग है, तो यह 1 + (3) + 4 + 1 + (3) मेमोरी का बाइट्स लेगा, (3) पैडिंग है, कुल 12 के लिए बाइट्स। 50% बर्बादी। स्वचालित लेआउट 1 + 1 + (2) + 4 = 8 बाइट्स के लिए पुन: व्यवस्थित करता है। केवल एक वर्ग में स्वचालित लेआउट होता है, संरचना में डिफ़ॉल्ट रूप से अनुक्रमिक लेआउट होता है।
अधिक स्पष्ट रूप से, एक बूल को C ++ प्रोग्राम में 32 बाइट्स की आवश्यकता हो सकती है जो एक आधुनिक C ++ कंपाइलर के साथ संकलित होती है जो AVX निर्देश सेट का समर्थन करता है। जो एक 32-बाइट संरेखण की आवश्यकता को लगाता है, बूल चर पैडिंग के 31 बाइट्स के साथ समाप्त हो सकता है। इसके अलावा कोर कारण। .NET घबराना SIMD निर्देशों का उत्सर्जन नहीं करता है, जब तक कि स्पष्ट रूप से लपेटा नहीं जाता है, यह संरेखण गारंटी नहीं प्राप्त कर सकता है।