2009-12-29 15 views
12

के लिए उद्देश्य-सी # परिभाषित निर्देश डायरेक्टिज्ड मैंने कई पोस्ट में पढ़ा है और ऐप्पल के कोड दिशानिर्देशों में ऑब्जेक्टिव-सी स्ट्रिंग स्थिरांक को बाहरी NSString *const MY_CONSTANT; के रूप में परिभाषित किया जाना चाहिए और #define निर्देश से बचा जाना चाहिए। ऐसा क्यों है? मुझे पता है कि #define प्रीकंपाइल समय पर चलाया जाता है लेकिन सभी स्ट्रिंग एक ही मेमोरी एड्रेस साझा करेंगे। मैंने जो एकमात्र लाभ पढ़ा था वह यह था कि यदि निरंतर अद्यतन या बदला जाना चाहिए तो आपको अपनी पूरी परियोजना को पुन: संकलित करने की आवश्यकता नहीं है। तो यही कारण है कि #define से बचा जाना चाहिए?स्ट्रिंग स्थिरांक

धन्यवाद

अद्यतन: इस मामले में एक #define उपयोग करने के लिए अच्छा है या वहाँ एक बेहतर तरीका है?

/* Constants Definition */ 
#define SERVER_URL @"http://subdomain.domain.edu.ar/Folder/" 
NSString *const ServerURL = SERVER_URL; 
NSString *const LoginURL = [email protected]"welcome.asp"; 
NSString *const CommandURL = [email protected]"com.asp"; 

उत्तर

-2

जहाँ तक मुझे पता है, #define केवल आप सी-शैली स्ट्रिंग स्थिरांक परिभाषित करने देता है। निरंतर एनएसएसटींग ऑब्जेक्ट बनाने के लिए, आपको इसे हेडर में घोषित करना होगा, और फिर इसे अपनी .m फ़ाइलों में से एक में एक मान दें।

हैडर फ़ाइल:

extern NSString *MyConstantString;

मुख्य फ़ाइल:

NSString *MyConstantString = @"String value";

+0

उद्देश्य # सी को परिभाषित क्यों करें "दुनिया" 'उद्देश्य-सी में काम नहीं करता है? – Dirk

+0

'# परिभाषित MyConstantString @" स्ट्रिंग मान "' काम नहीं करता है? – Chuck

+0

# परिभाषा सिर्फ एक टेक्स्ट प्रतिस्थापन करता है, इसलिए मुझे नहीं लगता कि क्यों # MSf @ "हैलो" काम नहीं करेगा – GuidoMB

10

यह जरूरी गारंटी नहीं है कि वहाँ केवल एक दिया स्ट्रिंग एक पूरे आवेदन में शाब्दिक के लिए एक NXConstantString वस्तु हो जाएगा। ऐसा लगता है कि अलग-अलग संकलन इकाइयों में एक ही स्थिर स्ट्रिंग के लिए अलग-अलग ऑब्जेक्ट हो सकते हैं। उदाहरण के लिए, यदि कोई प्लगइन लिखता है, तो प्लगइन में उस एनएसएसटींग शाब्दिक की घटनाओं के लिए एक निरंतर स्ट्रिंग उत्पन्न की जाएगी और मेजबान एप्लिकेशन में घटनाओं के लिए एक उत्पन्न किया जाएगा, और ये पॉइंटर-बराबर नहीं होंगे।

17

परिभाषा के विपरीत निरंतर उपयोग करने का एक व्यावहारिक कारण यह है कि आप isEqual: का उपयोग करने के बजाय प्रत्यक्ष तुलना (== का उपयोग कर) कर सकते हैं। पर विचार करें:

NSString * const kSomeStringConstant = @"LongStringConstantIsLong"; 
... 
[someArray addObject:kSomeStringConstant]; 
if ([someArray lastObject] == kSomeStringConstant) 
{ 
    ... 
} 

यह काम करेगा, क्योंकि == तुलना एक भी NSString वस्तु के समान स्थिरांक संकेत की तुलना की जाएगी। #define का उपयोग करना है, हालांकि:

#define STRING_CONSTANT @"MacrosCanBeEvil"; 
... 
[SomeArray addObject:STRING_CONSTANT]; // a new const `NSString` is created 
if ([someArray lastObject] == STRING_CONSTANT) // and another one, here. 
{ 
    ... 
} 

यह नहीं बाहर काम होता है, के बाद से दो तार अद्वितीय संकेत होगा। उन्हें प्रभावी ढंग से तुलना करने के लिए, आप isEqual:

if ([[someArray lastObject] isEqual:STRING_CONSTANT]) 
{ 
    ... 
} 

इस का उपयोग करते हुए सरल == तुलना से निष्पादन समय के संदर्भ में कहीं अधिक महंगा हो सकता है एक चरित्र-दर-चरित्र तुलना करने के लिए होगा।

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

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

+0

मुझे लगता है कि चक का जवाब मेरा विरोधाभास करता है, और मुझे यकीन नहीं है कि कौन सही है। –

+1

निरंतर "जगह में" दिखाई नहीं देगा जहां भी कोड में इसका इस्तेमाल किया गया था। दोनों तरीकों से NXConstantString ऑब्जेक्ट्स के संदर्भ उत्पन्न होंगे। यह सच है कि स्ट्रिंग अक्षर द्वारा अधिक उत्पन्न किया जा सकता है, लेकिन कोड में प्रत्येक स्ट्रिंग के लिए यह निश्चित रूप से एक वस्तु से बहुत कम होगा। – Chuck

+0

धन्यवाद। इससे – thesummersign

9

मैंने सुना है कि सबसे अच्छा तर्क यह है कि const स्ट्रिंग्स डीबगर में दिखाई देते हैं, जबकि मैक्रोज़ नहीं करते हैं।

+0

मदद मिली यह एक शानदार कारण है, आप "po" (प्रिंट ऑब्जेक्ट) को # परिभाषित निर्देश नहीं दे सकते। जैसा कि ई.जेम्स द्वारा इंगित किया गया है, यदि आपके स्थिरांक समकक्ष सभी सूचक हैं तो आप समानता के परीक्षण के लिए == का उपयोग कर सकते हैं। सभी अच्छे उत्तरों के लिए +1 है। – pchap10k

+0

समझ में आता है। :) – thesummersign

0
static NSString * const SERVER_URL = @"http://subdomain.domain.edu.ar/Folder/"; 
संबंधित मुद्दे