2011-03-29 4 views
13

Scala에서 다음과 같이 작성할 수 있습니까?스칼라 멤버에게 어떻게 위임 할 수 있습니까?

trait Road { 
    ... 
} 

class BridgeCauseway extends Road { 
    // implements method in Road 
} 

class Bridge extends Road { 
    val roadway = new BridgeCauseway() 

    // delegate all Bridge methods to the `roadway` member 
} 

또는 Road의 각 메서드를 하나씩 구현하고 roadway에서 해당 메서드를 호출해야합니까?

+6

참조 케빈 라이트의 자동 프록시 컴파일러 플러그인. –

+4

@ 대니얼 (Daniel) - 흥미롭게도, 나는 최근에 그 중 하나를 다시 해고했다. 2.9 컴파일러는 원래 설계를 지원할 수있는 것으로 변경되었습니다. –

+0

@kevin - 멋지다! 나는 모든 사람들이이 프록시 기능을 필요로한다고 생각한다. 확실히 scala의 표준 기능이어야합니다! 나는 항상 포워더를 쓰고 있는데, 나는 컴파일러 플러그인을 설치하는 게 너무 게으른 이유가 바로 그 것이다. 나는 그것을 설치하고 투명하게 그것을 사용하는 sbt, 아이디어 등을 설득 할 필요가있다. 프리젠 테이션 컴파일러에서 작동합니까 (예 : 아이디어)? –

답변

14

이 작업을 수행하는 가장 쉬운 방법은 대신 클래스 확장의 암시 적 변환 함께 Road 컬렉션에 Bridge를 저장하려고합니다. 다시 다시 Bridge를 얻을 필요가없는 경우

, 당신은 Any 반환 Roadowner 방법을 추가 BridgeCauseway에 대한 생성자 매개 변수를 사용하여 설정 한 다음 패턴 일치는 다리를 얻을 수 있습니다

trait Road { 
    def owner: Any 
    ... 
} 

class BridgeCauseway(val owner: Bridge) extends Road { . . . } 

class Bridge extends Road { 
    val roadway = new BridgeCauseway(this) 
    ... 
} 

myBridgeCauseway.owner match { 
    case b: Bridge => // Do bridge-specific stuff 
    ... 
} 
+0

암시적인 'Bridge'의 오브젝트 컴패니언을 왜 넣지 않으시겠습니까? 그러면 자동 전달이 보장됩니다. 물론, 메서드가 부작용 인 경우 원하는대로 작동하지 않을 수 있습니다. –

+0

@ 대니얼 - 동반자가 없었기 때문에하지 않았습니다. 그러나 나는 암묵적인'object bridge {...} '를 넣는 것이 일반적으로 원하는 것이라고 동의한다. –

+0

암시 적으로 child.parent로 자식을 대체 할 수 있지만 implicits를 사용하여 child를 child.parent.parent로 바꾸는 방법이 있습니까? –

3

의 경우 Bridgetrait으로 만들면 정렬됩니다.

scala> trait A { 
    | val x: String 
    | } 
defined trait A 

scala> class B extends A { 
    | val x = "foo" 
    | val y = "bar" 
    | } 
defined class B 

scala> trait C extends A { self: B =>   
    | val z = "baz"    
    | } 
defined trait C 

scala> new B with C 
res51: B with C = [email protected] 

scala> res51.x 
res52: java.lang.String = foo 

scala> res51.y 
res53: java.lang.String = bar 

scala> res51.z 
res54: java.lang.String = baz 
관련 문제