2010-07-29 13 views
7

मेरे पास एक टेम्पलेट है जो मैं तर्क के प्रकार के आधार पर सशर्त रूप से संकलित करना चाहता हूं। मुझे केवल "सादा पुराना डेटा" (पीओडी), यानी, पूर्णांक, आदि या वर्ग/structs के बीच अंतर करने की परवाह है। मैं विंडोज़ पर सी ++ वीएस 2008 का उपयोग कर रहा हूं।बूस्ट प्रकार-लक्षणों का उपयोग कर सशर्त संकलन

template<T> 
class foo 
{ 
    void bar(T do_something){ 
    #if IS_POD<T> 
     do something for simple types 
    #else 
     do something for classes/structs 
    #endif 
}} 

मैं बूस्ट लाइब्रेरी को देख रहा हूं और मैं देख सकता हूं कि वे जो चाहते हैं वह प्रतीत होता है। हालांकि, मुझे समझ में नहीं आता कि #if कथन के लिए सही वाक्यविन्यास क्या होगा।

किसी भी मदद की सराहना की जाएगी।


संपादित करें --- प्रतिक्रियाओं पढ़ने के बाद, मैं देख रहा हूँ मैं प्रश्न के अपने परिभाषा कुछ अनदेखी की। कक्षा foo एक टेम्पलेटेड क्लास है जिसे केवल bar के संस्करण को उदाहरण देने की आवश्यकता है जो class type T के लिए सही है। मैं एक ऐसे समाधान की तलाश में था जिसे संकलन समय का समाधान किया जा सके। उम्मीद है कि यह मेरी समस्या को साफ़ करता है।

उत्तर

7

आप enable_if बिना यह कर सकते हैं क्योंकि आप सभी की जरूरत प्रकार लक्षण के आधार पर प्रेषण करने के लिए है। enable_if का उपयोग ओवरलोड रिज़ॉल्यूशन से/टेम्पलेट इंस्टॉलेशन को जोड़ने/निकालने के लिए किया जाता है। आप अपने फ़ंक्शन में ऑब्जेक्ट पास करने के लिए सबसे अच्छी विधि चुनने के लिए कॉल गुणों का उपयोग करना चाह सकते हैं। एक नियम के रूप में, वस्तुओं को संदर्भ द्वारा पारित किया जाना चाहिए, जबकि पीओडी मूल्य से पारित किया जाता है। call_traits चलिए आप const और गैर-कॉन्स संदर्भों के बीच चुनते हैं। नीचे दिया गया कोड const संदर्भ का उपयोग करता है।

#include <boost/type_traits.hpp> 
#include <boost/call_traits.hpp> 

template <typename T> 
class foo { 
public: 
    void bar(typename boost::call_traits<T>::param_type obj) { 
     do_something(obj, boost::is_pod<T>()); 
    } 
private: 
    void do_something(T obj, const boost::true_type&) 
    { 
     // do something for POD 
    } 
    void do_something(const T& obj, const boost::false_type&) 
    { 
     // do something for classes 
    } 
}; 
0

प्रीप्रोसेसर का उपयोग करना संभव नहीं है। इसके बजाय Boost Enable If library पर एक नज़र डालें।

विशेष रूप से, आपके मामले में यह कैसा दिखेगा (परीक्षण नहीं):

void bar (typename enable_if <is_pod <T>, T>::type do_something) 
{ 
    // if is POD 
} 

void bar (typename disable_if <is_pod <T>, T>::type do_something) 
{ 
    // if not 
} 
+0

यह एक संकलन त्रुटि, एक बार वर्ग टेम्पलेट, instantiated है 'T' तय हो गई है हो जाएगा, और उस बिंदु पर आप' फोन bar' यह दो परिभाषा देखेंगे करने का प्रयास करते हैं और इसे संकलित करने के लिए असफल हो जायेगी उनमें से एक। ध्यान दें कि यह SFINAE नहीं है, क्योंकि यह प्रतिस्थापन विफलता नहीं होगी - प्रकार को सदस्य के तत्कालता से पहले तय किया गया है (या इसलिए मुझे लगता है, मैं इन चीजों के साथ कभी भी निश्चित नहीं हूं :))। –

3

आप पूर्वप्रक्रमक के साथ इस का समाधान नहीं कर के बाद से यह सी के बारे में पता नहीं है ++। (यह एक गूंगा पाठ प्रतिस्थापन उपकरण है।) ऐसा करने के लिए टेम्पलेट का उपयोग करें।

मान लिया जाये कि IsPod<T>::result रिटर्न कुछ एक जैसे Boolean<true>/Boolean<false>:,

template<T> 
class foo 
{ 
    void do_something(T obj, Boolean<true> /*is_pod*/) 
    { 
     // do something for simple types 
    } 
    void do_something(T obj, Boolean<false> /*is_pod*/) 
    { 
     // do something for classes/structs 
    } 

    void bar(T obj) 
    { 
     do_something(obj, IsPod<T>::result()); 
    } 
} 
संबंधित मुद्दे