Next-Squad/Interview-Question

[자바] 27. JAVA에서 바이트코드에 대해 설명해보세요.

jinan159 opened this issue · 1 comments

JAVA에서 바이트코드에 대해 설명해보세요.

파면 팔수록 심오한 내용이 많이 나오는 바이트코드...

키워드

ex) Java compiler, JIT Compiler, Lombok, Proxy

image

1. 바이트코드란?

바이트 코드란, JVM 이 읽을 수 있는 형태로 변환된 코드(.class)를 의미합니다.

OS 에 맞는 기계어로 번역하는 일은 JVM 이 수행하기 때문에 바이트코드는 특정 플랫폼(OS)에 종속적이지 않습니다.

이 덕분에 크로스 플랫폼을 지원하는 강력한 특징을 가지고 있습니다. = WORA(Write Once Run Anywhrer)

2. 런타임에서의 바이트코드

런타임에 바이트코드는 JVM 내부의 인터프리터JIT 컴파일러 에 의해 해당 OS에 맞는 기계어로 해석되어 실행됩니다.

사전에 기계어로 컴파일되는 C언어 등과는 다르게 실행 시간에 기계어로 해석되기 때문에, 상대적으로 느리다는 단점이 있습니다.

하지만, 이러한 단점을 극복하기 위해 {{JIT 컴파일러}}를 통해 인터프리팅을 최적화 합니다.

2.1 JIT 컴파일러

JIT 은 Just In Time 의 줄임말로, 제 시간에 라는 의미로 직역할 수 있는데요.

즉, 적절한 때에 컴파일하는 컴파일러 라는 의미로 해석할 수 있습니다.

JIT 컴파일러 *바이트코드*를 *기계어*로 미리 번역해놓는 역할을 하여, 인터프리터가 바이트코드를 읽는 시간을 절약하게 하여 실행 속도를 올리는 역할을 합니다.

그러나, 모든 바이트코드를 미리 번역하는게 아니라 일정한 조건이 만족되면 JIT 컴파일러가 동작하게 됩니다.

찾아보니 심오한 내용들이 더 있지만, 바이트코드라는 주제에서 벗어나는 내용인 것 같아 초간단 요약 및 참고 링크만 남겨둡니다.

(JIT 컴파일러에 대한 정확한 내용은 첨부한 링크를 참고해 주시기 바랍니다.)

3. 바이트코드 조작

바이트코드가 조작되는 시기는 컴파일 타임, 런타임 으로 나눌 수 있습니다.

3.1 컴파일 타임

대표적인 예로, 롬복이 있습니다.

롬복의 바이트코드 조작은 원래 읽기전용으로 제공되는 AST 를 수정하기 때문에, 해킹이라는 논란이 있습니다.

https://stackoverflow.com/a/6108573

image

대표적으로 롬복의 @Getter 어노테이션을 사용하면 실제 코드에는 없지만, 컴파일 완료된 바이트코드(.class)를 보면 Getter 코드가 있는것을 확인할 수 있습니다.

Java 컴파일러의 동작 과정 중 Annotation Processing 과정이 있는데, 여기서 Lombok 이 AST(Abstract Sytax Tree) 를 조작하기 때문입니다.

이 덕분에 우리는 보일러플레이트 코드를 작성하지 않고 깔끔한 소스코드를 유지할 수 있게 됩니다.

3.2 런타임

이 경우는 대표적인 예로 스프링의 Proxy 를 들 수 있는데요.

이는 #25 를 참고하시면 됩니다.