8
- C++ 11에서
override
specifier은 (서명이 일치하지 않기 때문에) 의도 한 가상 기본 기능을 재정의하지 않도록 보호합니다. final
specifier은 의도하지 않게 파생 클래스의 함수를 재정의하는 것을 방지합니다.
=> 지정자 알 수없는 기본 기능을 무시로부터 보호 (아마도 first
또는 no_override
같은)이 있습니까?C++`override` /`final` 지정자의 반대는 무엇입니까?
가상 함수가 파생 클래스의 기존 가상 함수와 같은 서명을 가진 기본 클래스에 추가 된 경우 컴파일러 오류가 발생합니다.
EDIT 4 : 여기, 관련 간단한 답변이 질문을 계속하려면 다시
- 추상화
원래 의사 코드
class B : A
는private: virtual void fooHasBeenDone() = 0;
class C : B
구현을 가지고private: virtual void fooHasBeenDone() override { react(); }
- 지금
class A
새로운 것을 얻습니다.private: virtual void fooHasBeenDone();
- 그러나 새
A::foo
은 원래B::foo
과 다를 수 있습니다.
과 구체적인 예 A PainterPath
class C : B
을 meaing
- 추상적 인
class B : A
가virtual void showPath() = 0;
지금virtual void showPath() override { mPath.setVisible(); }
class A
파일 경로 을 의미하는 새로운
- A가 showPath()를 호출하면 B는 일부 파일 경로 대신 painterPath를 표시합니다.
virtual void showPath();
를 얻을 구현
은 물론 이것은 잘못된 것입니다, 나는 다음 B::showPainterPath()
에 B::showPath()
의 이름을 바꿀뿐만 아니라 B::showPath() override
를 구현해야합니다. 나는 컴파일러로부터 정보를 얻고 싶다.
#include <iostream>
#define A_WITH_SHOWPATH
class A
{
#ifdef A_WITH_SHOWPATH
public:
void setPath(std::string const &filepath) {
std::cout << "File path set to '" << filepath << "'. Display it:\n";
showPath();
}
// to be called from outside, supposed to display file path
virtual void showPath() {
std::cout << "Displaying not implemented.\n";
}
#else
// has no showPath() function
#endif
};
class B : public A
{
public:
virtual void showPath() = 0; // to be called from outside
};
class C1 : public B {
public:
virtual void showPath() override {
std::cout << "C1 showing painter path as graphic\n";
}
};
class C2 : public B {
public:
virtual void showPath() override {
std::cout << "C2 showing painter path as widget\n";
}
};
int main() {
B* b1 = new C1();
B* b2 = new C2();
std::cout << "Should say 'C1 showing painter path as graphic':\n";
b1->showPath();
std::cout << "---------------------------\n";
std::cout << "Should say 'C2 showing painter path as widget':\n";
b2->showPath();
std::cout << "---------------------------\n";
#ifdef A_WITH_SHOWPATH
std::cout << "Should give compiler warning\n or say \"File path set to 'Test'. Display it:\"\n and \"Displaying not implemented.\",\n but not \"C1 showing painter path as graphic\":\n";
b1->setPath("Test");
std::cout << "# Calling setPath(\"Test\") on a B pointer now also displays the\n# PainterPath, which is not the intended behavior.\n";
std::cout << "# The setPath() function in B should be marked to never override\n# any function from the base class.\n";
std::cout << "---------------------------\n";
#endif
return 0;
}
실행을 텍스트 출력을 보면 다음과 같습니다
는 컴파일 실제 예를이다.참고로
, 특정 사용 케이스 (PainterPath 인스턴스)와 이전 예 :
아마도'-Wsuggest-override' GCC 옵션이 도움이 될 수도 있습니다. https://gcc.gnu.org/onlinedocs/gcc/Warning-Options.html – gavv
@gavv 그게 제가 찾고있는 것입니다. 플랫폼 독립적 인 방법이 있습니까? VS2012에서도 필요합니다. –
IMHO 이것은 디자인에 관한 질문입니다. Bathsheba가 언급했듯이, 기본 클래스에서 final을 사용할 때를 제외하고는 가능하지 않습니다. 또는 Leon이 언급 한 트릭을 사용할 수 있습니다. 인터페이스 클래스 목적을 위반하고 (http://coliru.stacked-crooked.com/a/17346a88fa6aaa89) 여기에 다른 문제가 있습니다. 마지막 편집에서 언급했듯이 함수의 이름을 다른 의미로 지정하면 안됩니다. 만약 당신이 정보를 얻으려면 몇 가지 분석 도구 (또한 Bathsheba imho가 여기에서 유일한 정답을 언급 함)를 사용하십시오. (IMHO) – user1810087