Java는 다른 객체에서 부모의 재정의 메소드를 호출 할 수 있지만 하위 유형은 없습니까?

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

  •  06-07-2019
  •  | 
  •  

문제

다음은 Java 코드가 작동합니다

class Cup {
    public String sayColor() {
        return "i have a color .";
    }
}

class TCup extends Cup{
    public String sayColor(){
        System.out.println(super.getClass().getName());
        return super.sayColor()+"color is tee green.";
    }
}

class MyTCup extends TCup {
    public String sayColor(){
        System.out.println(super.getClass().getName());
        return super.sayColor()+"but brushed to red now!";
    }
}
class Test {
    public static void main(String[] args) {
        Cup c = new MyTCup();
        System.out.print(c.sayColor());
    }
}

테스트 클래스 인쇄를 실행합니다

MyTCup
MyTCup
i have a color .color is tee green.but brushed to red now!

질문 1 : 런타임에서 객체 C 유형은 MyTcup이지만 항상 슈퍼 메소드를 호출 할 수 있습니다. 객체를 초기화 한 후 Mytcup 내에서 메모리에 메소드 스택이 있습니까? 그런 다음 코드와 같이 런타임에 호출 할 수 있습니까?

질문 2 : 다른 개체에서 수퍼 방법을 호출 할 방법이 없습니다. 아시다시피, C ++는 언제든지 상위 메소드를 호출하기 위해 캐스트 할 수 있습니다. Java에서 왜 다른가요?

도움이 되었습니까?

해결책

캡슐화를 위반하는 다른 객체에서 슈퍼 메소드를 호출 할 수 없습니다. 요점은 객체가 재정의 메소드가하는 일을 제어한다는 것입니다. 예를 들어, 컬렉션을 무시할 수 있습니다 add 방법 특정 상황에서 예외를 던지는 방법이므로 컬렉션에 "유효한"항목 만 추가 될 수 있습니다. 발신자가 캐스트로 우회 할 수 있다면 무의미합니다!

물체가 호출하는 유일한 이유 super.foo() 자체는 부모 구현을 사용하여 하나의 호출을 구현할 수 있도록하는 것입니다. 클래스의 코드에 달려있어서 현명하게 만 수행 할 수 있습니다. 다시, 컬렉션이 반복되는 경우 추가 수집 예제를 가져옵니다. add 가져야 할 것입니다 약간 검증 된 항목을 컬렉션에 추가하는 방법으로 super.add().

동일한 이유와 같은 이유로 조부모 구현이 아닌 부모 구현에 전화하십시오. super.foo() 유효하지만 super.super.foo() 그렇지 않습니다.

다른 팁

1:

귀하의 질문은 명확하지 않습니다. "코드처럼 런타임에 전화를 걸어"는 무엇을 의미합니까? 인스턴스 C가 슈퍼 클래스가 무엇인지 알고있는 경우, 클래스 계층 구조는 메모리에 저장되며 VM에서 액세스 할 수 있습니다.

2:

Java는 실제로 부모에게 인스턴스를 캐스팅 할 수 있습니다. 인스턴스에서 메소드를 호출하는 것은 항상 컴파일 타임 클래스가 아니라 인스턴스의 실제 클래스를 사용하는 것입니다. 즉, Java의 모든 방법은 C ++에서 "가상"이라고 불리는 것입니다. 이것이 내가 모르는 이유를 결정한 이유.

편집하다: 실제로 Jon Skeet은 왜 하위 클래스의 인스턴스에서 슈퍼 클래스의 메소드를 호출 할 수 없는지 매우 훌륭하게 설명합니다.

서브 클래스에서 새 헬퍼 메소드를 정의하여 원하는 것에 따라 슈퍼 방법을 호출 할 수있는 원본을 무시하지 않도록 할 수 있습니다.

실제로 할 수는 있지만 방법론을 사용해야하므로 코드에서만 작동합니다.
슈퍼 클래스에서는 다음과 같이 메소드에 매개 변수 "클래스"를 추가하십시오.

public String sayColor(Class classFilter){...

이제 모든 재정의에서 현재 하위 클래스가 지정된 필터 중 하나인지 확인하십시오.

if(TCup.class!=classFilter)return super.sayColor(classFilter);
return "some text for TCup only";

나는 독점적 인 방식으로 코딩했다. 더 많은 매개 변수를 추가하거나 NULL과 비교할 수 있으므로 Super Classment와 결과를 가입하고 창의성을 사용할 수 있습니다 :)

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