2011-10-31 18 views
8

पहले व्यक्ति को std::numeric_limits<size_t>::max() लगता है, लेकिन यदि कोई वस्तु बहुत बड़ी थी, तो क्या यह अभी भी एक-अतीत-अंत-अंत सूचक प्रदान कर सकता है? मुझे नहीं लगता। क्या इसका सबसे बड़ा मूल्य sizeof(T) है जो std::numeric_limits<size_t>::max()-1 उत्पन्न कर सकता है? क्या मैं सही हूँ, या क्या मुझे कुछ याद आ रही है?सबसे बड़ा मूल्य आकार (टी) क्या पैदा कर सकता है?

+0

क्या ऑब्जेक्ट * की आवश्यकता है * एक अतीत-अंत-अंत सूचक को प्रदान करने के लिए? – Dabbler

+0

@ डब्बलर: सी ++ मानक के अनुसार, हां, क्योंकि जहां तक ​​पॉइंटर अंकगणित का संबंध है, एक वस्तु को आकार 1 की सरणी के रूप में माना जा सकता है। यदि आप चाहें तो मैं सटीक शब्द देख सकता हूं। – fredoverflow

+0

@ माइक: गलत, 5.7 §1 कहता है 'इन ऑपरेटरों के प्रयोजनों के लिए, एक गैर-ऑब्जेक्ट ऑब्जेक्ट के लिए पॉइंटर पर पॉइंटर के समान व्यवहार करता है, जो ऑब्जेक्ट के प्रकार के साथ ऑब्जेक्ट के प्रकार के साथ लंबाई की सरणी का पहला तत्व होता है टाइप करें। ' – fredoverflow

उत्तर

3

प्रश्न: सबसे बड़ा मूल्य आकार (टी) क्या पैदा कर सकता है?

एक: std::numeric_limits<size_t>::max()

जाहिर है, sizeof std::numeric_limits<size_t>::max() से एक मूल्य के बड़ा नहीं लौट सकते, क्योंकि यह फिट नहीं होता। एकमात्र सवाल यह है कि, क्या यह ...::max() लौटा सकता है?

हां। यहां एक वैध प्रोग्राम है, जो सी ++ 03 मानक की कोई बाधा नहीं देता है, जो प्रमाण-दर-उदाहरण दिखाता है। विशेष रूप से, इस कार्यक्रम में §5.3.3 [expr.sizeof] सूचीबद्ध बाधा का उल्लंघन नहीं करता है, और न ही में §8.3.4 [dcl.array]:

#include <limits> 
#include <iostream> 
int main() { 
typedef char T[std::numeric_limits<size_t>::max()]; 
std::cout << sizeof(T)<<"\n"; 
} 
+0

क्या आपने वास्तव में प्रश्न को पूरी तरह से पढ़ा है? फ्रेड चर्चा करता है कि वह क्यों सोचता है कि यह गलत हो सकता है। प्रश्न के बाद आप 10 मिनट कैसे आ सकते हैं और बिना किसी बहस के अपने संदेहों का खंडन कर सकते हैं? – sbi

+0

+1, हालांकि सवाल यह बनी हुई है कि एक-अतीत-अंत-अंत सूचक का क्या मूल्य होगा। – Dabbler

+0

एचएम, जो मेरे कंप्यूटर पर '42 9 4 9 672 9 5 प्रिंट करता है, इसलिए मुझे लगता है कि मैं गलत था। – fredoverflow

0

यदि यह एक परीक्षण किया गया था, मैं यह कहना चाहता हूँ (size_t) -1

+2

यह 'std :: numeric_limits :: अधिकतम()' है। –

0

एक sizeof() अभिव्यक्ति प्रकार size_t के एक मूल्य अर्जित करता है। C99 मानक 6.5.3.4 से:

परिणाम का मूल्य कार्यान्वयन से परिभाषित है, और उसके प्रकार (एक अहस्ताक्षरित पूर्णांक प्रकार) size_t, stddef.h (और अन्य हेडर) में परिभाषित है।

इसलिए, अधिकतम मूल्य जो आकार() उत्पन्न कर सकता है वह SIZE_MAX है।

+2

यह अधिकतम मान है जिसे 'size_t' में संग्रहीत किया जा सकता है। इसका मतलब यह नहीं है कि 'sizeof'' size_t' के सभी मानों का उपयोग करता है। –

2

यह वास्तव में अच्छी तरह से परिभाषित नहीं है। लेकिन मानक के सुरक्षित सीमाओं के भीतर रहने के लिए, अधिकतम वस्तु आकार std::numeric_limits<ptrdiff_t>::max()

है कि क्योंकि जब आप दो संकेत घटाना, आप प्राप्त है एक ptrdiff_t

जो एक हस्ताक्षरित पूर्णांक प्रकार

चियर्स & hth है।,

+2

अफसोस की बात है, आपके पास 'std :: numeric_limits :: max()' से बड़ा सरणी हो सकती है। यदि आप इस सरणी के भीतर दो पॉइंटर्स घटाते हैं जो बहुत दूर हैं, तो व्यवहार अपरिभाषित है, [expr.add]/6 देखें। – avakar

+0

@avakar: मैं शापित हो जाऊँगा! अच्छा लगता है। 'किसी भी अन्य अंकगणित अतिप्रवाह के साथ, यदि परिणाम प्रदान की गई जगह में फिट नहीं होता है, तो व्यवहार अपरिभाषित होता है। – fredoverflow

3

यदि आप एक एक पास्ट अंत सूचक से इसे करने के लिए एक सूचक को घटा कर आकार std::numeric_limits<size_t>::max() की एक वस्तु के आकार की गणना कर सकते हैं std::numeric_limits<ptrdiff_t>::max() > std::numeric_limits<size_t>::max()

यदि sizeof(T*) > sizeof(size_t) यदि आपके पास उस ऑब्जेक्ट के अंदर प्रत्येक बाइट को संबोधित करने के लिए पर्याप्त विशिष्ट पॉइंटर्स हो सकते हैं (यदि आपके पास char की सरणी है, उदाहरण के लिए) प्लस वन-अतीत के लिए एक।

तो, एक कार्यान्वयन लिखना संभव है जहां sizeofstd::numeric_limits<size_t>::max() लौटा सकता है, और जहां आप बड़े ऑब्जेक्ट के एक-अतीत के अंत में पॉइंटर प्राप्त कर सकते हैं।

+1

यदि कार्यान्वयन सेगमेंट किए गए पते वाले प्लेटफ़ॉर्म को लक्षित करता है, तो' sizeof (T *)> sizeof (size_t) 'आसानी से हो सकता है सच हो। –

+0

"मुझे संदेह है कि ऐसा एक कार्यान्वयन है [जहां 'आकार'' std :: numeric_limits :: अधिकतम() '] वापस कर सकता है"। जी ++ एक ऐसा कार्यान्वयन है। –

0

आपके पास एक मानक अनुपालन कंपाइलर हो सकता है जो ऑब्जेक्ट आकारों की अनुमति देता है जो पॉइंटर अंकगणित को बहने का कारण बनता है; हालांकि, परिणाम अपरिभाषित है। सी ++ मानक से, 5.7 [expr।जोड़ने]:

जब एक ही सरणी वस्तु के तत्वों के लिए दो संकेत घटाया जाता है, परिणाम दो सरणी तत्वों की सबस्क्रिप्ट का अंतर है। परिणाम का प्रकार कार्यान्वयन-परिभाषित हस्ताक्षरित अभिन्न प्रकार है; <cstddef> हेडर (18.2) में इस प्रकार का एक ही प्रकार होगा जिसे std::ptrdiff_t के रूप में परिभाषित किया गया है। किसी अन्य अंकगणित अतिप्रवाह के साथ, यदि परिणाम प्रदान की गई जगह में फिट नहीं होता है, तो व्यवहार अपरिभाषित है।

1

किसी सरणी के अंत से परे इंगित करने की आवश्यकता size_t की सीमा से कोई लेना देना नहीं है। x ऑब्जेक्ट को देखते हुए, (&x)+1 के लिए एक वैध सूचक होने के लिए यह काफी संभव है, भले ही दो पॉइंटर्स को अलग करने वाले बाइट्स की संख्या size_t द्वारा प्रदर्शित नहीं की जा सके।

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

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