2014-06-09 10 views
5

मैं निम्नलिखित कोड है:प्लस सूचक अधिक भार टेम्पलेट सूचक को

template<class A, class B> 
void test(A& a, const B* b) 
{ std::cout << "hi" << std::endl; } 

template<class A, class B> 
void test(A& a, const B** b) 
{ std::cout << "hello" << std::endl; } 

class TestClass 
{}; 


int main() 
{ 
    int a = 5; 
    TestClass b; 
    TestClass* c = &b; 
    test(a, &c); 
    return 0; 
} 

किसी तरह उत्पादन "हाय" हालांकि ऐसा लगता है कि बेहतर मैच दूसरा टेम्पलेट समारोह होगा। जब मैं const एस को क्वालीफायर के रूप में B* और B** पर हटा देता हूं तो मुझे "हैलो" मिलता है जो दूसरे टेम्पलेट फ़ंक्शन से मेल खाता है। संकलक इस मामले में कॉल करने के लिए फ़ंक्शन का चयन कैसे करता है? धन्यवाद!

उत्तर

1

अन्य उत्तरों सही ढंग से ध्यान देते हैं कि T** से const T** तक कोई अंतर्निहित रूपांतरण नहीं है और इसलिए ओवरलोड में से कोई भी व्यवहार्य नहीं है। मैं समझाऊंगा कि इस रूपांतरण की अनुमति क्यों नहीं है। यह वास्तव में मानक में एक उदाहरण के रूप में लिखा जाता है। पैरा 4.4, के शब्दों में

[नोट: यदि एक कार्यक्रम प्रकार स्थिरांक टी ** (अर्थात, अगर लाइन # 1 नीचे की अनुमति दी गई है), एक की एक सूचक के प्रकार टी ** की एक सूचक आवंटित कर सकते हैं प्रोग्राम अनजाने में एक कॉन्स ऑब्जेक्ट को संशोधित कर सकता है (जैसा कि यह लाइन # 2 पर किया जाता है)। उदाहरण के लिए,

int main() { 
    const char c = ’c’; 
    char* pc; 
    const char** pcc = &pc; // #1: not allowed 
    *pcc = &c; 
    *pc = ’C’; // #2: modifies a const object 
} 
3

को देखते हुए T** से T const** दूसरे के लिए कोई रूपांतरण सभी में एक मैच (ऐसी कोई रूपांतरण है क्योंकि यह एक const वस्तु को गैर const उपयोग की अनुमति होती है) है है कि वहाँ नहीं। हालांकि, T** से T* const* में एक रूपांतरण है। इस प्रकार, संबंधित अधिभार केवल व्यवहार्य और उपयोग किया जाता है।

3

&c एक TestClass** जो const TestClass** को TestClass* const * लेकिन नहीं करने के लिए प्रोत्साहित किया जा सकता है।

आप test<int, TestClass>(a, &c); का उपयोग करके त्रुटि को मजबूर कर सकते हैं जो आपको असंभव रूपांतरण दिखाएगा।

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