2

그래서 이진 표현식, 단항 식, 모두 추상식으로 구성된 표현식의 클래스 구조를 가지므로 Add, Sub, Mul과 같은 특정 구체 클래스로 확장됩니다. , 아닙니다, 등등 ... 그런 것.자바 - 동일한 클래스 구조에 대한 다중 방문자 패턴

Class Structure

나는 이러한 클래스 각각에 대해 2 방문자를 만들려고합니다. 하나는 toString이고 하나는 표현식을 평가합니다 (값 계산).

문제는 내 toStringVisitor는 항상 String을 반환해야하지만 evaluateVisitor는 연산에 따라 변수 유형을 반환합니다 (예 : Add는 int를 반환하고 Lower는 부울을 반환하고 그렇지 않으면 다른 반환 함). 유형도 포함)

2 명의 방문자에 대해 2 개의 방문자 인터페이스를 만들지 않도록 할 수 있습니까? 나는 단지 evaluateVisitor과하지의 toString 방문자를 위해 작동합니까 지금

public interface Visitor { 

Public int visit(Neg c); 
Public int visit(Add c); 
Public int visit(Sub c); 
Public int visit(Mul c); 
Public boolean visit(Lowerthan c); 
Public boolean visit(Greaterthan c); 
Public boolean visit(Equal c); 
Public boolean visit(Not c); 
Public boolean visit(And c); 
Public boolean visit(Or c); 

} 

무슨 예를 들어

.

또한, 예를 들어, 사용의 차이점은 무엇입니까 :

Public int visit(Neg c); 
Public int visit(Add c); 
Public int visit(Sub c); 
Public int visit(Mul c); 

Public int visitNeg(Neg c); 
Public int visitAdd(Add c); 
Public int visitSub(Sub c); 
Public int visitMul(Mul c); 

나는 동적 바인딩 문제를 방지하기 위해 방문 방법을 차별화해야하지만, 난 못해 정말 들었다 그 이유가 무엇인지 파악하십시오.

interface Visitor<R> { 
    R visit(Neg c); 
    ... 
} 

그래서 당신의 ToStringVisitor이 Visitor<String>을 구현하는 것이고, 다른 두 Visitor<Integer>Visitor<Boolean>을 구현합니다

답변

4

당신은 일반 방문자를 만들 수 있습니다.

visitNeg()와는 달리 visit()을 사용하는 것과 관련하여 선택의 문제입니다. 별개의 이름을 사용하면 API가 혼란스럽게 느껴집니다. 오버로드를 사용하면 이해하기 쉽고 버그가 발생하기 쉽습니다. 나는 개인적으로 과부하의 큰 팬이 아니다.

+0

이 문제를 구현하는 데 문제가 있습니다. 예를 들어 변수 반환 유형이 필요한 클래스가 있습니다. 그리고 Im 각각의 Evaluate 방문자를'public visit (Sequence c)'와 같이 컴파일하려고하는데, Im은'Evaluator.java:147 : error : invalid method declaration; 반환 유형 필요 공개 visitSequence (시퀀스 c)' – spacing

+0

알맞은 구문을 얻지 못했습니다. 이제 클래스의 제네릭 이름을 정의해야한다는 것을 깨달았고 메서드에서 대괄호를 다시 사용하지 않습니다. – spacing