क्या सी में टाइप्डिफ़ और # डिफाइन समान हैं?


जवाबों:


122

नहीं।

#defineएक प्रीप्रोसेसर टोकन है: संकलक स्वयं इसे कभी नहीं देखेगा।
typedefएक संकलक टोकन है: प्रीप्रोसेसर को इसकी परवाह नहीं है।

आप एक ही प्रभाव प्राप्त करने के लिए एक या दूसरे का उपयोग कर सकते हैं, लेकिन अपनी आवश्यकताओं के लिए उचित एक का उपयोग करना बेहतर है

#define MY_TYPE int
typedef int My_Type;

जब चीजें "बालों वाली" हो जाती हैं, तो उचित उपकरण का उपयोग करना सही बनाता है

#define FX_TYPE void (*)(int)
typedef void (*stdfx)(int);

void fx_typ(stdfx fx); /* ok */
void fx_def(FX_TYPE fx); /* error */

3
टंकण के बाद stdfx, उस प्रकार की वैध वस्तुएं उन कार्यों की ओर संकेत करती हैं जो एक इंट प्राप्त करते हैं और एक मान नहीं लौटाते हैं।
दोपहर जू

1
तर्क के रूप में फ़ंक्शन सूचक के आवरण में #define विफल क्यों होगा?
अल्लाहजाने

2
@Allahjane: विस्तार हो जाता है void fx_def(void (*)(int) fx);; सही घोषणा है void fx_def(void (*fx)(int));
दोपहर

5
फ़ंक्शन पॉइंटर्स मैक्रो के साथ उल्लेखनीय हैं, केवल अगर आप वाक्यविन्यास छोड़ने के लिए तैयार हैं #define FX_TYPE(f) void (*f)(int):। तब आप अपने कार्य को इस प्रकार घोषित करेंगे:void fx_def(FX_TYPE(fx));
प्लेफर

229

typedefचर जैसे नियमों का पालन करना, जबकि defineसंकलन इकाई के अंत तक (या एक मिलान तक undef) मान्य रहता है ।

साथ ही, कुछ चीजें ऐसी भी की जा सकती हैं, जिनके साथ typedefनहीं किया जा सकता है define
उदाहरण के लिए:

typedef int* int_p1;
int_p1 a, b, c;  // a, b, c are all int pointers

#define int_p2 int*
int_p2 a, b, c;  // only the first is a pointer, because int_p2
                 // is replaced with int*, producing: int* a, b, c
                 // which should be read as: int *a, b, c
typedef int a10[10];
a10 a, b, c;  // create three 10-int arrays
typedef int (*func_p) (int);
func_p fp;  // func_p is a pointer to a function that
            // takes an int and returns an int

23

नहीं, वे एक समान नहीं हैं। उदाहरण के लिए:

#define INTPTR int*
...
INTPTR a, b;

प्रीप्रोसेसिंग के बाद, वह रेखा फैल जाती है

int* a, b;

उम्मीद है कि आप समस्या देखते हैं; केवल aप्रकार होगा int *; bएक सादा घोषित किया जाएगा int(क्योंकि *घोषणाकर्ता के साथ जुड़ा हुआ है, न कि प्रकार निर्दिष्टकर्ता)।

इसके विपरीत

typedef int *INTPTR;
...
INTPTR a, b;

इस मामले में, दोनों aऔर bटाइप होंगे int *

टंकण की पूरी कक्षाएं हैं जो एक प्रीप्रोसेसर मैक्रो के साथ उत्सर्जित नहीं की जा सकती हैं, जैसे कि फ़ंक्शन या गिरफ्तार करने के लिए संकेत:

typedef int (*CALLBACK)(void);
typedef int *(*(*OBNOXIOUSFUNC)(void))[20]; 
...
CALLBACK aCallbackFunc;        // aCallbackFunc is a pointer to a function 
                               // returning int
OBNOXIOUSFUNC anObnoxiousFunc; // anObnoxiousFunc is a pointer to a function
                               // returning a pointer to a 20-element array
                               // of pointers to int

प्रीप्रोसेसर मैक्रो के साथ ऐसा करने का प्रयास करें।


13

#define मैक्रोज़ को परिभाषित करता है।
टाइपेडिफ प्रकारों को परिभाषित करता है।

अब कह रहे हैं कि, यहाँ कुछ अंतर हैं:

#Define के साथ आप उन कंटेस्टेंट्स को परिभाषित कर सकते हैं जिनका उपयोग संकलन समय में किया जा सकता है। स्थिरांक के साथ इस्तेमाल किया जा सकता #ifdef जाँच कैसे कोड संकलित किया गया है, और संकलन मानकों के अनुसार कुछ कोड विशेषज्ञ।
आप लघु खोज और मैक्रो कार्यों को बदलने के लिए #define का उपयोग कर सकते हैं ।

टाइपीडिफ का उपयोग उपनामों को देने के लिए किया जा सकता है (जो आप शायद #define के साथ भी कर सकते हैं), लेकिन यह #define स्थिरांक की प्रकृति को खोजने और बदलने के कारण सुरक्षित है।
इसके अलावा, आप टाइपडिफ़ के साथ आगे की घोषणा का उपयोग कर सकते हैं जो आपको एक प्रकार की घोषणा करने की अनुमति देता है जिसका उपयोग किया जाएगा, लेकिन अभी तक उस फ़ाइल से जुड़ा नहीं है जिसे आप लिख रहे हैं।


#define की प्रकृति को खोजने और बदलने का क्या मतलब है? , धन्यवाद
मोहम्मद एल शेनावी

1
संकलन से पहले इसका मतलब है, प्रीप्रोसेसर सभी मैक्रोज़ को ढूंढेंगे और उन्हें उनके मूल सिंटैक्स के साथ बदल देंगे
प्रिंस विजय प्रताप

"टाइपसीफ का उपयोग उपनामों को देने के लिए किया जा सकता है" यह मेरे लिए उद्देश्य समझा, धन्यवाद।
डेव वॉयल्स

8

प्रीप्रोसेसर मैक्रोज़ (" #defineएस") एक लेक्सिकल रिप्लेसमेंट टूल हैं "ला एंड रिप्लेस"। वे प्रोग्रामिंग भाषा के पूरी तरह से अज्ञेय हैं और आपको जो कुछ भी करने की कोशिश कर रहे हैं उसकी कोई समझ नहीं है। आप उन्हें महिमामंडित कॉपी / पेस्ट मैकेनिक के रूप में सोच सकते हैं - कभी-कभी यह उपयोगी होता है, लेकिन आपको इसका उपयोग सावधानी से करना चाहिए।

टाइपेडिफ्स एक सी भाषा सुविधा है जो आपको प्रकारों के लिए उपनाम बनाने की सुविधा देती है। यह जटिल यौगिक प्रकार (जैसे संरचना और फंक्शन पॉइंटर्स) को पठनीय और सुपाच्य बनाने के लिए अत्यंत उपयोगी है (C ++ में ऐसी स्थितियाँ भी हैं जहाँ आपको एक प्रकार लिखना आवश्यक है )।

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


क्या आप C ++ में एक उदाहरण बता सकते हैं जहां आपको एक प्रकार लिखना चाहिए? मैं बस उस बारे में उत्सुक हूं।
jyz

@jyzuz: यदि आप सदस्य फ़ंक्शन फ़ंक्शन की एक सरणी वापस करने के लिए कोई सदस्य फ़ंक्शन चाहते हैं, या ऐसा कुछ है - यदि आप टाइप करने का प्रयास करते हैं, तो जीसीसी वास्तव में कहता है "आपको एक टाइपिडिफ का उपयोग करना चाहिए"।
केरेक एसबी

4

वे बहुत अलग हैं, हालांकि उनका उपयोग अक्सर कस्टम डेटा प्रकारों को लागू करने के लिए किया जाता है (जो कि मैं इस सवाल को मान रहा हूं)।

जैसा कि पीएमजी ने उल्लेख किया है, #defineकंपाइलर कोड को देखने से पहले प्री-प्रोसेसर (जैसे कट-एंड-पेस्ट ऑपरेशन) द्वारा संभाला जाता है और कंपाइलर typedefद्वारा व्याख्या की जाती है।

मुख्य अंतरों में से एक (कम से कम जब यह डेटा प्रकारों को परिभाषित करने की बात आती है) यह है कि typedefअधिक विशिष्ट प्रकार की जाँच के लिए अनुमति देता है। उदाहरण के लिए,

#define defType int
typedef int tdType

defType x;
tdType y;

यहां, कंपाइलर वेरिएबल x को एक इंट के रूप में देखता है, लेकिन वेरिएबल y को 'tdType' नामक डेटा टाइप के रूप में होता है जो इंट के समान आकार का होता है। यदि आपने एक फ़ंक्शन लिखा है, जो टाइप डिफेक्ट का एक पैरामीटर लेता है, तो कॉल करने वाला एक सामान्य इंट पास कर सकता है और कंपाइलर को अंतर नहीं पता होगा। यदि इसके बजाय फ़ंक्शन ने tdType का एक पैरामीटर लिया, तो कंपाइलर यह सुनिश्चित करेगा कि फ़ंक्शन कॉल के दौरान उचित प्रकार के एक चर का उपयोग किया गया था।

इसके अलावा, कुछ डीबगर्स के पास typedefएस को संभालने की क्षमता होती है , जो कि सभी कस्टम प्रकारों को उनके अंतर्निहित आदिम प्रकारों के रूप में सूचीबद्ध करने की तुलना में अधिक उपयोगी हो सकता है (जैसा कि #defineइसके बजाय इसका उपयोग किया गया था)।


2

नहीं
टाइपसीफ एक सी कीवर्ड है जो एक प्रकार के लिए एक उपनाम बनाता है।
#define एक पूर्व-प्रोसेसर निर्देश है, जो संकलन से पहले एक पाठ प्रतिस्थापन घटना बनाता है। जब संकलक कोड में जाता है, तो मूल "# परिभाषित" शब्द अब नहीं है। # डिफाइन का उपयोग ज्यादातर मैक्रोज़ और वैश्विक स्थिरांक के लिए किया जाता है।


2
शब्द "पॉइंटर" के उपयोग से यहां कुछ भ्रम हो सकता है।

माना। इसलिए मैं वापस चला गया और एमएसडीएन पर टाइपडेफ़ के लिए एक लिंक जोड़ दिया - बस अगर भविष्य में कोई भी इस सवाल का उपयोग करेगा तो यह पता लगाएगा कि टाइपडिफ क्या है। लेकिन शायद मुझे उस शब्द को बदलना चाहिए ...
ट्रैवलिंग टेक गाय

2

AFAIK, नहीं।

typedefमौजूदा डेटा प्रकार के लिए "उपनाम" सेट करने में आपकी सहायता करता है। उदाहरण के लिए। typedef char chr;

#defineमैक्रो या सामान्य पैटर्न प्रतिस्थापन को परिभाषित करने के लिए एक प्रीप्रोसेसर निर्देश का उपयोग किया जाता है। उदाहरण के लिए। #define MAX 100, सभी घटनाओं को MAX100 में बदल देता है


0

जैसा कि ऊपर उल्लेख किया गया है, #defineटाइपपैड के बीच एक महत्वपूर्ण अंतर है । इसके बारे में सोचने का सही तरीका यह है कि एक टाइप्डेफ को पूर्ण "एन्कैप्सुलेटेड" प्रकार के रूप में देखा जाए। इसका मतलब है कि आप इसे घोषित करने के बाद इसे जोड़ नहीं सकते।

आप अन्य प्रकार के विनिर्देशक के साथ एक मैक्रो टाइपनेम का विस्तार कर सकते हैं, लेकिन एक टाइप किए गए टाइफनाम का नाम नहीं:

#define fruit int
unsigned fruit i;   // works fine

typedef int fruit;
unsigned fruit i;   // illegal

इसके अलावा, एक टाइप-डी नाम एक घोषणा में हर घोषणाकर्ता के लिए प्रकार प्रदान करता है।

#define fruit int *
fruit apple, banana;

मैक्रो विस्तार के बाद, दूसरी पंक्ति बन जाती है:

int *apple, banana;

Apple एक इंट का सूचक है, जबकि केला एक int है। तुलना में। इस प्रकार एक टाइफाइड:

typedef char *fruit;
fruit apple, banana;

सेब और केला दोनों को समान घोषित करता है। मोर्चे पर नाम अलग है, लेकिन वे दोनों एक चार के संकेत हैं।


-1

जैसा कि सभी ने कहा, वे समान नहीं हैं। अधिकांश उत्तर इससे typedefअधिक लाभकारी होने का संकेत देते हैं #define। लेकिन मुझे एक प्लस पॉइंट देना चाहिए #define:
जब आपका कोड बहुत बड़ा है, कई फाइलों में बिखरा हुआ है, तो इसका उपयोग करना बेहतर है #define; यह पठनीयता में मदद करता है - आप इसकी घोषणा के स्थान पर एक चर की वास्तविक प्रकार की परिभाषा को देखने के लिए सभी कोड को प्रीप्रोसेस कर सकते हैं।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.