C/C++과 비교한 자바의 실행과정

Jina·2024년 7월 3일
0

Java

목록 보기
1/1
post-custom-banner

보통 프로그래밍 언어를 처음 배우면 C언어로 프로그래밍에 입문한다.
요즘은 파이썬으로 입문하지만...라떼는 C/C++이다
하지만 우리나라는 자바 공화국이고...특히 백엔드 개발을 시작하면 자바는 필수적이라서 자바는 무조건 알아야 한다.
그리고 이때 자바를 배우는 과정에서 자연스럽게 기존에 알았던 C언어와 비교를 하게 된다.
나 또한 이러했고, 따라서 이를 정리해보려고 한다.

먼저, C/C++에서 소스코드가 실행되는 과정부터 알아보자.

  1. 전처리 (.c -> .i)
    '#include', '#define'과 같이 '#'으로 시작하는 전처리기 구문을 처리한다.

  2. 컴파일 (.i -> .s)
    소스코드를 어셈블리어로 바꿔준다.

  3. 어셈블 (.s -> .o)
    어셈블러가 어셈블리어를 오브젝트 코드로 바꿔준다. 이 오브젝트 코드를 기계어라고 한다. 즉, 기계가 드디어 제대로 이해할 수 있다는 소리!

  4. 링크 (.o + .a(라이브러리 파일) -> .exe 또는 .out)
    링커가 여러가지 오브젝트 파일들과 라이브러리 파일들을 하나로 합쳐 묶어서 실행파일로 생성해준다.

그리고 이 모든 과정을 합해서 빌드라고 한다.

그렇다면 자바에서는 빌드 과정이 어떻게 이루어질까?

  1. 컴파일 (.java -> .class)
    자바 소스코드가 바이트코드로 변환된다.

  2. 클래스로더
    바이트코드를 JVM으로 끌고 들어가는데, 여기에서 링크 과정이 이루어진다.

  3. 실행엔진
    JVM에 올라온 바이트코드들을 명령어 단위로 하나씩 가져와서 실행한다. 이때 인터프리트와 컴파일 두가지 방식을 병행한다.

    인터프리터: 바이트코드를 하나씩 읽어서 실행한다. 이때 하나씩 실행할 때는 빠르지만, 전체적인 속도는 느리다는 단점이 있어서 다음의 컴파일 과정이 도입된다.

    JIT 컴파일러: 인터프리터의 단점을 보완하기 위해 도입되었다. 바이트코드 전체를 컴파일해서 바이너리코드로 변경한다. 이때 변경된 바이너리코드가 기계어이다.


왜 이렇게 다를까?

C언어는 운영체제에 종속받는 언어이다. 운영체제가 CPU에 맞는 언어로 변환시켜주기 때문이다.
그런데 자바는 JVM이라는 가상머신을 통해 운영체제에 종속받지 않고, 독립적으로 실행할 수 있다.
이 JVM 때문에 이런 차이가 생기지 않았을까 생각한다.

과정을 정리해보자면,

두 언어 모두 컴파일 과정이 있는데, 해당 과정은 공통적으로 개발자가 작성한 소스코드를 전체적으로 다른 코드로 변환해주는 과정이다.
물론 C/C++은 그 결과물이 운영체제에 종속적인 어셈블리 코드고, 자바는 JVM이 이해할 수 있는 언어인 바이트코드이다.
그 이후, C/C++은 먼저 기계어로 바꾼 뒤 링크 과정을 수행하지만, 자바는 먼저 링크 과정을 수행하고 난 뒤 JVM에서 기계어인 바이너리코드로 변경된다.
또한 C/C++은 순수하게 컴파일만 수행되는 언어라면, 자바는 JVM 내에서 컴파일과 인터프리트가 같이 수행되면서 하이브리드 언어가 되었다.

post-custom-banner

0개의 댓글