C++:을 피할 수 있는 방법"잘못된 공변환 입력에서"클래스를 상속하지 않고 캐스팅?

StackOverflow https://stackoverflow.com/questions/2410532

  •  18-09-2019
  •  | 
  •  

문제

나는 꽤 복잡하는 클래스 계층 구조의 클래스는 다음과 같이에 따라 각각 다른:두 가지가 있 추상 클래스에서는 A 와 C 를 포함하는 방법을 반환하는 인스턴스의 C 고,각각합니다.에서 자신의 클래스를 상속하고 싶을 사용하고 변 형에 있는 이 경우 문제가하지 않기 때문에 나는 방법을 알고 있어 전향을 선언 상속에 관하여 선박이다.

을 구하는"시험합니다.cpp:22:오류:잘못된 공변환 입력을 위해'가 D*B::outC()'"오류문 컴파일러가 있다는 것을 알고하지 않습니 D 은 서브 클래스의 C.

class C;

class A {
public:
        virtual C* outC() = 0;
};

class C {
public:
        virtual A* outA() = 0;
};


class D;

class B : public A {
public:
        D* outC();
};

class D : public C {
public:
        B* outA();
};

D* B::outC() {
        return new D();
}

B* D::outA() {
        return new B();
}

변경하는 경우에 반환한 유형의 B::outC()C*예 컴파일.이 있을 유지하는 방법 B*D*로 반품 유형에서 상속되는 클래스(이것은 것이 직관적이 나는 방법이 있다)?

도움이 되었습니까?

해결책

나는 C ++에서 직접 공분산 회원을 결합시키는 방법이 없다는 것을 알고 있습니다. 레이어를 추가하거나 공분산을 구현해야합니다.

첫 번째 옵션

class C;

class A {
public:
        virtual C* outC() = 0;
};

class C {
public:
        virtual A* outA() = 0;
};


class BI : public A {
public:
};

class D : public C {
public:
        BI* outA();
};

class B: public BI {
public:
        D* outC();
};

D* B::outC() {
        return new D();
}

BI* D::outA() {
        return new B();
}

그리고 두 번째

class C;

class A {
public:
        C* outC() { return do_outC(); }
        virtual C* do_outC() = 0;
};

class C {
public:
        virtual A* outA() = 0;
};


class D;

class B : public A {
public:
        D* outC();
        virtual C* do_outC();
};

class D : public C {
public:
        B* outA();
};

D* B::outC() {
        return static_cast<D*>(do_outC());
}

C* B::do_outC() {
        return new D();
}

B* D::outA() {
        return new B();
}

이 두 번째 옵션은 컴파일러가 암시 적으로 수행 한 것입니다 (일부 정적 검사가 static_cast가 유효한지 확인).

다른 팁

으로 지금까지 내가 아는 방법이 없다,이것을 하지 않고 명시적으로 캐스팅.는 것이 문제의 정의 클래스 B 알 수 없다는 D 의 하위 클래스 C 까지 그 본체의 정의 클래스 D, 지만,의 정의 클래스 D 알 수 없다는 B 의 하위 클래스 A 까지 그 본체의 정의 클래스 B, 고,그래서 당신이 원형을 의미할 수 있습니다.이는 해결할 수 없으로 앞으로 선언하기 때문에 앞으로 선언 불행하게도 지정할 수 없습니다 상속 관계입니다.

거의 비슷한 문제로 구현하려고 공변 clone() 방법 템플릿을 사용하여, 는 내가 발견될 수 있는 해결, 지만,그 유사한 솔루션이 여전히 실패하기 때문에 여기의 순환을 참조 남아 불가능한 해결합니다.

클라이언트 측면 기대로 인해이 작업을 수행 할 수 없습니다. C 인스턴스를 사용하는 경우 어떤 종류의 C인지 알 수 없습니다 (A D 또는 다른 것). 따라서 B 포인터 (파생 클래스로의 호출에서 결과하지만 컴파일 타임에 알지 못하는) B 포인터를 A 포인터에 저장하면 모든 메모리가 올바른지 확실하지 않습니다.

다형성 유형의 메소드를 호출 할 때 런타임 환경은 동적 유형의 객체를 확인해야하며 클래스 계층에 맞게 포인터를 움직입니다. 당신이 공분산에 의존해야한다고 확신하지 못합니다. 살펴보십시오 이것

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top