खोज…


टिप्पणियों

एक पैरामीटर या एक आभासी सदस्य फ़ंक्शन m लिए रिटर्न वैल्यू का कोविरेंस वह जगह है जहां इसका प्रकार T एक व्युत्पन्न वर्ग ' m ओवरराइड में अधिक विशिष्ट हो जाता है। T तब तब भिन्नता ( भिन्नता ) में उसी तरह से ( सह ) वर्ग के रूप में ( m ) प्रदान करता है। C ++ covariant रिटर्न प्रकारों के लिए भाषा समर्थन प्रदान करता है जो कच्चे पॉइंटर्स या कच्चे संदर्भ हैं - covariance पॉइंटर्टी या रेफरेंट प्रकार के लिए है।

C ++ समर्थन सीमित प्रकारों तक सीमित है क्योंकि फ़ंक्शन रिटर्न मान C ++ में केवल शुद्ध आउट-तर्क हैं , और covariance केवल शुद्ध आउट-तर्क के लिए सुरक्षित है। अन्यथा कॉलिंग कोड प्राप्त कोड अपेक्षा से कम विशिष्ट प्रकार की वस्तु की आपूर्ति कर सकता है। MIT के प्रोफेसर बारबरा लिस्कॉव ने इसकी और संबंधित भिन्न प्रकार की सुरक्षा के मुद्दों की जांच की, और अब इसे Liskov प्रतिस्थापन सिद्धांत, या LSP के रूप में जाना जाता है।

कोवरियन समर्थन अनिवार्य रूप से डाउनकास्टिंग और गतिशील प्रकार की जाँच से बचने में मदद करता है।

चूंकि स्मार्ट पॉइंटर वर्ग प्रकार के होते हैं, इसलिए कोई स्मार्ट पॉइंटर परिणाम के लिए सीधे सहसंयोजक के लिए अंतर्निहित समर्थन का उपयोग नहीं कर सकता है, लेकिन एक स्पष्ट रूप से covariant गैर- virtual स्मार्ट पॉइंटर परिणाम आवरण को covariant virtual फ़ंक्शन के लिए परिभाषित कर सकता है जो कच्चे संकेत देता है।

1. सहिष्णु रिटर्न के बिना आधार उदाहरण, दिखाता है कि वे वांछनीय क्यों हैं

// 1. Base example not using language support for covariance, dynamic type checking.

class Top
{
public:
    virtual Top* clone() const = 0;
    virtual ~Top() = default;       // Necessary for `delete` via Top*.
};

class D : public Top
{

public:
    Top* clone() const override
    { return new D( *this ); }
};

class DD : public D
{
private:
    int answer_ = 42;

public:
    int answer() const
    { return answer_;}

    Top* clone() const override
    { return new DD( *this ); }
};

#include <assert.h>
#include <iostream>
#include <typeinfo>
using namespace std;

int main()
{
    cout << boolalpha;

    DD* p1 = new DD();
    Top* p2 = p1->clone();
    bool const  correct_dynamic_type = (typeid( *p2 ) == typeid( DD ));
    cout << correct_dynamic_type << endl;               // "true"

    assert( correct_dynamic_type ); // This is essentially dynamic type checking. :(
    auto p2_most_derived = static_cast<DD*>( p2 );
    cout << p2_most_derived->answer() << endl;          // "42"
    delete p2;
    delete p1;
}

2. आधार उदाहरण, स्थिर प्रकार की जाँच का सहसंयोजक परिणाम संस्करण।

// 2. Covariant result version of the base example, static type checking.

class Top
{
public:
    virtual Top* clone() const = 0;
    virtual ~Top() = default;       // Necessary for `delete` via Top*.
};

class D : public Top
{
public:
    D* /* ← Covariant return */ clone() const override
    { return new D( *this ); }
};

class DD : public D
{
private:
    int answer_ = 42;

public:
    int answer() const
    { return answer_;}

    DD* /* ← Covariant return */ clone() const override
    { return new DD( *this ); }
};

#include <iostream>
using namespace std;

int main()
{
    DD* p1 = new DD();
    DD* p2 = p1->clone();
    // Correct dynamic type DD for *p2 is guaranteed by the static type checking.

    cout << p2->answer() << endl;          // "42"
    delete p2;
    delete p1;
}

3. सहसंयोजक स्मार्ट सूचक परिणाम (स्वचालित सफाई)।

// 3. Covariant smart pointer result (automated cleanup).

#include <memory>
using std::unique_ptr;

template< class Type >
auto up( Type* p ) { return unique_ptr<Type>( p ); }

class Top
{
private:
    virtual Top* virtual_clone() const = 0;

public:
    unique_ptr<Top> clone() const
    { return up( virtual_clone() ); }

    virtual ~Top() = default;       // Necessary for `delete` via Top*.
};

class D : public Top
{
private:
    D* /* ← Covariant return */ virtual_clone() const override
    { return new D( *this ); }

public:
    unique_ptr<D> /* ← Apparent covariant return */ clone() const
    { return up( virtual_clone() ); }
};

class DD : public D
{
private:
    int answer_ = 42;

    DD* /* ← Covariant return */ virtual_clone() const override
    { return new DD( *this ); }

public:
    int answer() const
    { return answer_;}

    unique_ptr<DD> /* ← Apparent covariant return */ clone() const
    { return up( virtual_clone() ); }
};

#include <iostream>
using namespace std;

int main()
{
    auto  p1 = unique_ptr<DD>(new DD());
    auto  p2 = p1->clone();
    // Correct dynamic type DD for *p2 is guaranteed by the static type checking.

    cout << p2->answer() << endl;          // "42"
    // Cleanup is automated via unique_ptr.
 }


Modified text is an extract of the original Stack Overflow Documentation
के तहत लाइसेंस प्राप्त है CC BY-SA 3.0
से संबद्ध नहीं है Stack Overflow