[अपडेट 2016/01/31]
कुछ के रूप में नहीं किया है मेरे पहले के जवाब की तरह क्योंकि यह स्ट्रिंग तुलनाओं की आवश्यकता के बिना लक्ष्य को पूरा करके ओपी के पूरे compile time string compare
पहलू से से बचा है, यहां एक और विस्तृत उत्तर दिया गया है।
आप नहीं कर सकते! सी 9 8 या सी 99 में नहीं। सी 11 में भी नहीं। मैक्रो मैनिपुलेशन की कोई मात्रा इसे बदल नहीं देगी।
की परिभाषा #if
में प्रयुक्त स्ट्रिंग की अनुमति नहीं देती है।
इसलिए यदि आप अपने आप को वर्णों तक सीमित आप इस का उपयोग कर सकते यह वर्णों की अनुमति देता है:
#define JACK 'J'
#define QUEEN 'Q'
#define CHOICE JACK // or QUEEN, your choice
#if 'J' == CHOICE
#define USER "jack"
#define USER_VS "queen"
#elif 'Q' == CHOICE
#define USER "queen"
#define USER_VS "jack"
#else
#define USER "anonymous1"
#define USER_VS "anonymous2"
#endif
#pragma message "USER IS " USER
#pragma message "USER_VS IS " USER_VS
आप कर सकते हैं! सी ++ 11 में। यदि आप तुलना के लिए संकलन समय सहायक कार्य परिभाषित करते हैं।
// compares two strings in compile time constant fashion
constexpr int c_strcmp(char const* lhs, char const* rhs)
{
return (('\0' == lhs[0]) && ('\0' == rhs[0])) ? 0
: (lhs[0] != rhs[0]) ? (lhs[0] - rhs[0])
: c_strcmp(lhs+1, rhs+1);
}
// some compilers may require ((int)lhs[0] - (int)rhs[0])
#define JACK "jack"
#define QUEEN "queen"
#define USER JACK // or QUEEN, your choice
#if 0 == c_strcmp(USER, JACK)
#define USER_VS QUEEN
#elif 0 == c_strcmp(USER, QUEEN)
#define USER_VS JACK
#else
#define USER_VS "unknown"
#endif
#pragma message "USER IS " USER
#pragma message "USER_VS IS " USER_VS
तो, अंत में, आप जिस तरह से आप USER
और USER_VS
के लिए अंतिम स्ट्रिंग मूल्यों को चुनने के अपने लक्ष्य accomlish बदलने के लिए होगा।
आप सी 99 में संकलन समय स्ट्रिंग तुलना नहीं कर सकते हैं, लेकिन आप स्ट्रिंग का चयन करने के समय संकलित कर सकते हैं।
यदि आपको वास्तव में तुलनात्मक समय की तुलना करने के लिए संकलित समय करना होगा, तो आपको उस सुविधा को अनुमति देने वाले C++ 11 या नए रूपों में बदलना होगा।
[मूल जवाब इस प्रकार है]
प्रयास करें:
#define jack_VS queen
#define queen_VS jack
#define USER jack // jack or queen, your choice
#define USER_VS USER##_VS // jack_VS or queen_VS
// stringify usage: S(USER) or S(USER_VS) when you need the string form.
#define S(U) S_(U)
#define S_(U) #U
अद्यतन: एएनएसआई टोकन चिपकाने कभी कभी स्पष्ट से कम है। ;- डी
एक मैक्रो से पहले एक #
डालने से इसे अपने मूल्य की स्ट्रिंग में बदल दिया जाता है, इसके नंगे मूल्य के बजाय।
दो टोकन के बीच एक डबल ##
डालने से उन्हें एक टोकन में संयोजित किया जाता है।
तो, मैक्रो USER_VS
विस्तार jack_VS
या queen_VS
, तुम कैसे USER
सेट के आधार पर है।
स्ट्रिंग मैक्रो S(...)
मैक्रो इंडिकेशन का उपयोग करता है इसलिए नामित मैक्रो का मान स्ट्रिंग में परिवर्तित हो जाता है। मैक्रो के नाम के बजाय।
इस प्रकार USER##_VS
jack_VS
(या queen_VS
) बन जाता है, इस पर निर्भर करता है कि आप USER
कैसे सेट करते हैं।
बाद में, जब stringify मैक्रो (इस उदाहरण में jack_VS
) S(USER_VS)
रूप USER_VS
का मूल्य प्रयोग किया जाता है अविवेक कदम S_(jack_VS)
जो एक स्ट्रिंग "queen"
में अपने मूल्य (queen
) धर्मान्तरित करने के लिए पारित कर दिया है।
यदि आप USER
से queen
पर सेट करते हैं तो अंतिम परिणाम स्ट्रिंग "jack"
है।
टोकन संयोजन के लिए देखें: https://gcc.gnu.org/onlinedocs/cpp/Concatenation.html
टोकन स्ट्रिंग रूपांतरण के लिए, देखें: [। UPDATED 2015/02/15 लिखने में कोई त्रुटि को दूर करने के] https://gcc.gnu.org/onlinedocs/cpp/Stringification.html#Stringification
आप स्ट्रैम्प का उपयोग क्यों नहीं कर सकते? –
@ ब्रायन: हाँ, मैंने भी प्रश्न पढ़ा :-)। बस यह सुनिश्चित करना चाहता था कि वह स्ट्रैम्प मौजूद है, और प्रतिक्रिया प्रबुद्ध हो सकती है, क्योंकि मैं यह # डिफाईन सामान करने का कोई कारण नहीं सोच सकता। –
बस यह उल्लेख करना चाहता था कि वही चीज नियमित कोड के लिए भी जाती है, न केवल पूर्वप्रचारक। एक साधारण मूल्य कब करेंगे जब स्ट्रिंग का उपयोग न करें। स्ट्रिंग्स में पूर्णांक या enums की तुलना में अधिक ओवरहेड होता है और यदि आपको उनकी तुलना करने से कुछ और करने की आवश्यकता नहीं है, तो तार गलत समाधान हैं। – swestrup