컴파일러

  • 전체 변환: 소스 코드 전체 읽어 한 번에 기계어로 번역. 변환 과정 거친 후 생성된 기계어 코드를 실행.
  • 속도: 컴파일 과정은 시간이 걸리지만, 변환된 코드는 직접 실행되므로 실행 시간 빠름.
  • C, C++, Rust, Go
  • 코드 수정시 컴파일 과정 필요.

인터프리터

  • 한 줄씩 변환: 소스 코드 한 줄씩 읽어 가며 바로 기계어로 변환하고 실행.
  • 속도: 컴파일 단계 없어 초기 단계는 빠름. 전체 코드 실행 시간은 컴파일러 사용하는것 보다 느릴 수 있다. 코드 실행할 때마다 변환과정 거치기 때문.
  • 코드 수정시 컴파일 과정 불필요.

모두 고수준 언어를 기계어로 변환한다는 공통점 있다.

JIT 컴파일러

JIT 컴파일러는 인터프리터와 컴파일러 중간 형태

  1. 코드 분석: 실행 시점에 코드 분석하여, 어떤 부분이 가장 자주 실행되는지(hot spot) 판단. (즉, 실행전 코드를 분석하지는 않음)
  2. 동적 컴파일: 분석 결과에 기반하여, 자주 실행되는 코드(핫 스팟)만 선별적으로 기계어로 변환. 이과정은 프로그램 실행중에 실시간으로 이루어짐.
  3. 최적화: 컴파일 과정에서 다양한 최적화 기법 사용(ex, 메모리 접근 패턴을 분석, 가비지 컬렉션의 오버헤드 최소화 등)
  4. 실행: 컴파일된 기계어 코드를 실행. 프로그램이 실행되면서 새로운 핫 스팟 발견되면, 해당 부분도 JIT 컴파일 통해 최적화됨 ex) JVM, .NET, V8

자주 사용되는 코드의 실행 속도가 크게 향상되는 것이라는 장점과 컴파일된 코드를 메모리에 저장해 캐싱하기 때문에 인터프리터 방식에 비해 더 많은 메모리 소비하는 단점 있다.