오랜만에 JAVA를 복습하려고 책을 읽다가 헷갈리는 부분이 생겼다.
책 내용
자바에서 정수 리터럴의 기본형은 int형이다.
이때 리터럴(Literal)이란 코드에 직접 작성한 값을 의미한다.
(추가로 찾아보니 데이터 그 자체, 변수에 넣어 변하지 않는 데이터를 의미한다.)
정수의 자료형은 byte, short, int, long 네 가지이며 크기는 각각 1B, 2B, 4B, 8B이다.
byte형 변수에 리터럴 할당의 경우
byte a = 4;
위의 코드에서 byte 자료형 변수 a에 4를 저장했을 때 4는 기본형인 int형이지만
byte자료형의 범위에 포함되기 때문에 자동으로 형변환이 되어서 byte로 저장된다.
byte형 변수에 연산 결과가 할당될 경우
byte a = 3;
byte b = 4;
byte c = a + b; // 오류 발생

byte + byte 연산 시 CPU의 최소 연산 단위가 int이기 때문에 int보다 작은 자료형도 일단 int로 읽어와서 연산을 수행한다.
즉 byte + byte의 연산 코드이지만 int + int 연산이 진행되었기 때문에 결과도 int형이 되고 위의 코드에서 오류가 발생한다.
헷갈린 부분
위의 두 가지 부분을 각각 읽었을 때 의문이 들었다.
byte a = 4; 의 경우 4가 int형이지만 자동으로 형변환이 되어서 byte로 저장이 되는데
byte + byte의 연산 결과를 byte 자료형에 저장할 때에는 자동으로 형변환이 안되고 오류가 생기는 이유가 뭘까?
분석 결과와 해결법
위 두 가지 경우 차이의 핵심은 컴파일에 있었다.
자바 소스코드(.java 파일)를 바이트코드(.class 파일)로 변환하는 컴파일 과정에서
byte a = 4; (byte형 변수에 리터럴 할당)의 경우 4가 byte범위에 있는지 검사하기 때문에 이 과정에서 자동으로 형변환이 이루어진다.

실제로 byte범위를 넘어가는 리터럴을 대입하면 컴파일 과정에서 에러가 발생한다.
byte c = a + b;(byte형 변수에 연산 결과가 할당)의 경우 실제로 a + b의 연산이 아닌 a(byte) + b(byte)의 결과가 int형이고
컴파일 시에는 int형인 결과가 byte의 범위에 포함되는지 알 수 없기 때문에 에러가 발생한다.
따라서 이 경우에는 형변환 코드를 추가해줘야 한다.

자바는 타입 안정성을 중요시하는 언어임과 컴파일 단계에서 변수 타입, 연산, 형변환 등 관련 오류를 미리 검사하는 과정의 구체적인 예시를 공부하는 경험이었다.