2011-06-19 6 views
13

चेक बाहर हैपूर्णांक 4 बाइट है, लेकिन अभी भी यह चार में संग्रहित किया जा सकता क्यों इस कार्यक्रम नहीं अतिप्रवाह

#include<stdio.h> 

int main(){ 

char c='a'; 
printf("%d %d", sizeof(c),sizeof('a')); 
} 

उत्पादन 1 4
मैं जानता हूँ कि जब हम एक बयान चार c = लिखना है 'एक' ; क्यों कोई अतिप्रवाह आदि

+1

कंपाइलर स्मार्ट है। :) –

+3

उत्सुकता से, 'आकार (' ए ')' सी और सी ++ के बीच अंतरों में से एक है (इसलिए उत्तरार्द्ध पूर्व का सख्त सुपरसेट नहीं है): सी में, 'sizeof (' a ') == sizeof (int) ', सी ++ में, 'sizeof (' a ') == sizeof (char) == 1'। –

उत्तर

15

पहले, एएनएसआई प्रति/आईईसी 9899: 1999 (ई) §6.4.4.4:

  10. एक पूर्णांक चरित्र निरंतर प्रकार int है। एक पूर्णांक वर्ण निरंतर का मान एक एकल वर्ण जिसमें एक एकल बाइट निष्पादन वर्ण को मानचित्रित किया गया है एक पूर्णांक के रूप में व्याख्या किए गए मैप किए गए वर्ण के प्रतिनिधित्व का संख्यात्मक मान है। [...]

§6.5.3.4:

  2. sizeof ऑपरेटर अपनी संकार्य के आकार (बाइट्स में) है, जो एक अभिव्यक्ति या की parenthesized नाम हो सकता है पैदावार एक प्रकार। आकार ऑपरेंड के प्रकार से निर्धारित किया जाता है। [...]

  3. जब एक संकार्य टाइप चार, अहस्ताक्षरित चार, या हस्ताक्षर किए चार, (या उसके एक योग्य संस्करण) है कि परिणाम है 1. [...]

के लिए आवेदन किया

जैसा कि आप देख सकते हैं, int के लिए, sizeof('a') के लिए हमें sizeof(int) मिलता है, जो आपके प्लेटफ़ॉर्म पर 4 है।हालांकि, sizeof(c) के लिए, हम जो होने के लिए 1.

तो क्यों न हम 'a' एक char को असाइन कर सकते परिभाषित किया गया है एक char के आकार, मिल सकता है?

§6.5.16.1:

  2. सरल काम (=) में, सही संकार्य के मूल्य में काम अभिव्यक्ति के प्रकार में बदल जाती है और द्वारा नामित वस्तु में संग्रहीत मूल्य बदल देता है बाएं ऑपरेंड।

तो, int कि है 'a' परोक्ष एक char में बदल जाती है। वहां भी एक उदाहरण है, स्पष्ट रूप से दिखा रहा है कि int एस को char पर स्पष्ट रूप से परिवर्तित किया जा सकता है।

+5

और यदि आप * वास्तव में * pedantic होना चाहते हैं, तो 6.3.1.3/1 उद्धृत करें, "यदि मूल्य को नए प्रकार में दर्शाया जा सकता है, तो यह अपरिवर्तित है", और 6.2.5/3, "' char' बड़ा है मूल निष्पादन चरित्र सेट ", और 5.2.1/3" के किसी भी सदस्य को स्टोर करने के लिए पर्याप्त मूल निष्पादन वर्ण सेट होगा ... लैटिन वर्णमाला के 26 लोअरकेस अक्षर ":-) –

1

है

तो यह कैसे होता है कि 1 बाइट (चार ग) 4 बाइट (ASCII कोड) में से कुछ बात की अंतरिक्ष में संग्रहीत किया जाता है "एक चरित्र शाब्दिक प्रकार int है" (http://publib.boulder.ibm.com/infocenter/lnxpcomp/v7v91/index.jsp?topic=%2Fcom.ibm.vacpp7l.doc%2Flanguage%2Fref%2Fclrc02ccon.htm)

लेकिन सी आप की सुविधा देता है सैद्धांतिक रूप से "असुरक्षित" स्वचालित डाले - यह उदाहरण के लिए करने के लिए ठीक है,

char c = 34; 

भी 34 यद्यपि स्पष्ट रूप से में एक 4-बाइट है टी। यह सुरक्षित बनाता है कि आप जानते हैं कि जब आप 'ए' लिखते हैं तो यह वास्तव में 1 एसीआई चरित्र है और इसलिए 1 बाइट है।

रास्ते से अच्छा सवाल - मुझे थोड़ा उलझन में डाल दिया।

2

संकलक पूरी तरह से int को char में परिवर्तित करता है।

int i = 42; 
char c = i * 2 - 4; 

अंतिम पंक्ति के रूप संकलक द्वारा व्याख्या की है कि:

char c = (char)(i * 2 - 4); 

ये implicit type conversions संकलक द्वारा नियंत्रित किया जाता है - कोई "अतिप्रवाह बफ़र"। (char) को आंतरिक रूप से संभाला जाता है (मशीन द्वारा स्वयं, संभवतः int जैसे साधारण प्रकारों के लिए)। यह उचित बाइट्स पर उचित रूप से कटौती करता है और "हस्ताक्षर" (+/-) को संरक्षित करता है।

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