[SCALA] 어떻게 스칼라 특성은 자바 바이트 코드로 컴파일?
SCALA어떻게 스칼라 특성은 자바 바이트 코드로 컴파일?
나는 잠시 지금을 위해 스칼라와 함께 주변에 연주 한 나는 특성이 인터페이스와 추상 클래스 모두의 스칼라와 동등한 역할을 할 수 있음을 알고있다. 정확히 어떻게 특성은 자바 바이트 코드로 컴파일?
내가 언급 한 특성을 정확히 그렇지 않으면 추가 클래스 Java 인터페이스 가능한 경우, 인터페이스와 같은 컴파일 몇 가지 짧은 설명을 발견했다. 스칼라 클래스 선형화, 자바에서 사용할 수없는 기능을 달성하는 방법을 나는 아직도, 그러나, 이해가 안 돼요.
특성은 자바 바이트 코드로 컴파일하는 방법을 설명하는 좋은 소스가 있습니까?
해결법
-
==============================
1.나는 전문가가 아니지만, 여기 나의 이해는 다음과 같습니다
나는 전문가가 아니지만, 여기 나의 이해는 다음과 같습니다
형질 인터페이스 및 대응하는 클래스로 컴파일된다.
trait Foo { def bar = { println("bar!") } }
동등하게 ...
public interface Foo { public void bar(); } public class Foo$class { public static void bar(Foo self) { println("bar!"); } }
푸 $ 클래스의 정적 줄 방법이 어떻게 호출되는 않는 : 어떤 질문을 남긴다? 이 마법은 푸 특성이 혼합되어있는 클래스의 컴파일러에 의해 수행된다.
class Baz extends Foo
같은됩니다 ...
public class Baz implements Foo { public void bar() { Foo$class.bar(this); } }
클래스 선형화 단지 언어 사양에 정의 된 선형 규칙에 따른 방법의 적절한 버전합니다 (XXXX $ 클래스 클래스의 정적 메소드를 호출)를 구현합니다.
-
==============================
2.이를 살펴보기 위해, 모두 추상적이고 구체적인 방법과 여러 특성을 사용하여 다음 스칼라의 예를 살펴 보자 :
이를 살펴보기 위해, 모두 추상적이고 구체적인 방법과 여러 특성을 사용하여 다음 스칼라의 예를 살펴 보자 :
trait A { def foo(i: Int) = ??? def abstractBar(i: Int): Int } trait B { def baz(i: Int) = ??? } class C extends A with B { override def abstractBar(i: Int) = ??? }
순간 (스칼라 2.11로서, 즉) 한 특성은 다음과 같이 인코딩된다 :
이 부호화의 주요 장점은 콘크리트 부재가없는 특성이 (인터페이스 동형이다) 실제로 인터페이스로 컴파일된다는 것이다.
interface A { int foo(int i); int abstractBar(int i); } abstract class A$class { static void $init$(A $this) {} static int foo(A $this, int i) { return ???; } } interface B { int baz(int i); } abstract class B$class { static void $init$(B $this) {} static int baz(B $this, int i) { return ???; } } class C implements A, B { public C() { A$class.$init$(this); B$class.$init$(this); } @Override public int baz(int i) { return B$class.baz(this, i); } @Override public int foo(int i) { return A$class.foo(this, i); } @Override public int abstractBar(int i) { return ???; } }
그러나, 스칼라 2.12 자바 (8)이 필요하며, 따라서 사용하는 기본 방법 및 인터페이스에 정적 메서드 등이 같은 결과 외모에 할 수있다 :
interface A { static void $init$(A $this) {} static int foo$(A $this, int i) { return ???; } default int foo(int i) { return A.foo$(this, i); }; int abstractBar(int i); } interface B { static void $init$(B $this) {} static int baz$(B $this, int i) { return ???; } default int baz(int i) { return B.baz$(this, i); } } class C implements A, B { public C() { A.$init$(this); B.$init$(this); } @Override public int abstractBar(int i) { return ???; } }
당신이 볼 수 있듯이, 정적 방법과 전달자와 기존의 디자인을 유지하고있다, 그들은 단지 인터페이스에 접혀. 형질의 구체적인 방법은 이제 정적 방법으로 인터페이스 자체로 이동 한 전달자 방법은 모든 클래스에서 합성되지만 기본 방법으로 한 번 정의하고 (형질의 본문에 코드를 나타냅니다) $ 방법 초기화 정적의 $되지 않습니다 동반자 정적 클래스가 필요하고,뿐만 아니라 인터페이스로 이동되었습니다.
그것은 아마도 다음과 같이 단순화 할 수 있습니다 :
interface A { static void $init$(A $this) {} default int foo(int i) { return ???; }; int abstractBar(int i); } interface B { static void $init$(B $this) {} default int baz(int i) { return ???; } } class C implements A, B { public C() { A.$init$(this); B.$init$(this); } @Override public int abstractBar(int i) { return ???; } }
나는이 작업이 완료되지 않은 이유를 모르겠어요. 언뜻 보면, 현재의 인코딩이 우리에게 전달 호환성의 비트를 줄 수 있습니다 당신이 이전 컴파일러로 컴파일 된 클래스와 새로운 컴파일러로 컴파일 특성을 사용할 수 있습니다, 그 오래된 클래스는 단순히 그들과의 인터페이스에서 상속 방법 전달자 기본을 무시합니다 동일한 사람. 전달자 방법 달러 (A $) 클래스와 B의 $ 클래스 더 이상 존재는, hypothetic 전달 호환성이하는 그래서 실제로 작업에 정적 메소드를 호출하려고합니다 제외.
-
==============================
3.이것의 아주 좋은 설명입니다 :
이것의 아주 좋은 설명입니다 :
바쁜 자바 프로그래머를위한 스칼라 입문 : 특성과 행동의 - JVM의 특색
인용문:
-
==============================
4.스칼라 (12)와 자바 (8)의 맥락에서, 당신은 8020cd6 커밋 다른 설명을 볼 수 있습니다 :
스칼라 (12)와 자바 (8)의 맥락에서, 당신은 8020cd6 커밋 다른 설명을 볼 수 있습니다 :
interface T { default int m() { return 1 } static int m$(T $this) { <invokespecial $this.m()> } } class C implements T { public int m() { return T.m$(this) } }
from https://stackoverflow.com/questions/2557303/how-are-scala-traits-compiled-into-java-bytecode by cc-by-sa and MIT license
'SCALA' 카테고리의 다른 글
[SCALA] 스칼라의지도를 반전하는 우아한 방법 (0) | 2019.11.08 |
---|---|
[SCALA] GZIP 형식은 스파크에서 지원됩니까? (0) | 2019.11.08 |
[SCALA] 왜 배열의 불변하지만,리스트는 공변? (0) | 2019.11.08 |
[SCALA] 스칼라 일반적인 방법 - T 없음 ClassTag 가능 (0) | 2019.11.08 |
[SCALA] 어떻게 스칼라 가변 인자 방법으로 스칼라 배열을 전달하는? (0) | 2019.11.08 |