2014-04-02 2 views
1

나는 루트 객체와 동일하게 대부분의 호출을 전달하는 래퍼 클래스를 작성하고 있었고 실수로 (매개 변수 이름 x 등의) 전체 정의를 다음과 같이 남겼습니다. 놀랍게도, 그것은 컴파일되었습니다. 그럼 여기서 무슨 일이 일어나고있는거야? 이것은 root.p_에 할당하는 것과 비슷합니까? 나는 그것이 "x"라는 이름을 부탁에 남겨 둘 수 있다는 것이 이상하다는 것을 알았다. 또한 랩된 통화를 전달하는 가장 빠른 (가장 빠른) 방법은 무엇입니까?이것은 왜 컴파일되고 무슨 일이 일어나고 있습니까?

trait A { 
    def p(x:Int) = println("A"+123) 
} 

case class B(root:A) { 

    def p(x: Int): Unit = root.p(x:Int) // WHAT HAPPENED HERE? 
} 

object Test extends App { 
    val temp = new A{} 
    val b = B(temp) 
    b.p(123) 
} 

답변

2

은 무슨 일 귀속을 입력하고, 여기에 훨씬 아니다.

은 코드가 의도 한대로

def p(x: Int): Unit = root.p(x) 

을 쓴 것처럼 작동합니다. 전화에서 x: Int을 쓸 때 (완전히 다른 의미가있는 선언이 아니라) 또는 더 일반적으로는 expr: Type 일 때 expr과 같은 값을 갖지만 expr이 주어진 유형인지 확인하도록 컴파일러에 지시합니다 이것은 컴파일 유형, 업 캐스트의 일종의 확인, 전혀 실행 체크 (예 : asInstanceOf[...])이 아니며이를 처리하기 위해 해당 유형을 가지고 있는지 확인합니다. 여기에서 x는 실제로 Int이고 컴파일러가 Int로 처리하므로 ascription이 아무 것도 변경하지 않습니다. 두 번째 호출에서는 귀속으로, 컴파일러가 3임을 알고

def f(a: Any) ... 
def f(i: Int) ... 

f(3) // calls f(i: Int) 
f(3: Any) // calls f(a: Any) 

참고 :

코드 어딘가에 아닌 명백한 유형을 문서화 외에 입력 귀속는 오버로드 된 메서드 중 하나를 선택하기 위해 사용될 수있다 Any이고 정확도는 Int보다 작지만 여전히 사실입니다. 그렇지 않으면 오류가 발생합니다. 이것은 캐스트가 아닙니다. 그러나이 구속은 다른 버전의 f을 호출하게합니다.

당신은 자세한 내용은 그 대답을 봐 가질 수 있습니다 https://stackoverflow.com/a/2087356/754787

+0

위대한 답변! 이제 왜 구문이 유용한 지 이해합니다 ... – LaloInDublin

0

당신은 A.pB.p의 구현을 위임하고 있습니까?

root.p(x:Int)을 제외하고 나는 이상한 것을 볼 수 없다. root.p(x)으로 타이핑을 줄일 수있다.

특성이 코드 믹스 인의 방법이다, 나는 가장 쉬운 방법이라고 생각 :

trait A { 
    def p(x: Int) = println("A" + x) 
} 

case class B extends AnyRef with A 

val b = B() 
b.p(123) 
+0

덕분에, 내 예제 코드의 더 큰 조각을 입증하기 위해 단지이다. – LaloInDublin

관련 문제