프로그램을 작성하다 보면 서로 다른 데이터 타입을 연산하는 경우가 발생 할 수 있다.
연산을 수행하기 위해선 데이터타입을 일치시켜야 하는데, 이때 발생하는 변환이 형변환 이라고 한다.
boolean
을 제외한 타입끼리는 서로 형변환이 가능하.
그 방법은 "(타입)피연산자" 이다.
ex)
double d = 85.4;
int score = (int)d; //85
//연산을 할 때만 피연산자를 읽고 변환하기 때문에, 피연산자의 값은 변화가 없다.
범위가 큰 타입을, 작은 타입으로 변환하면 값의 손실이 생길 것이다.
4byte인 int
를 1byte인 byte
로 변환하는 경우, 아래와 같이 변할 것 이다.
int a = 300; //300
byte b = (byte)a; //44
int
: ...0 | ...0 | 0000001 | 00101100 이고,
byte
: | 00101100 로 변환이 된기 때문에, 10진수로 44가 되는 것이다.
특히 실수형이 포함된 경우, double
과 float
의 정밀도 차이를 고려하여야 한다.
double
이 float
으로 변환되는 경우 23이후의 가수의 값은 버려지고,
반대의 경우는 가수의 24번째 자리에서 반올림이 발생한다.
가수의 차이로 같은 수를 저장해도 double
과 float
의 차이가 발생 할 수 있다.
class Casting{
public static void main(String[] args){
float f = 9.1234567f;
double d = 9.1234567;
double d2 = (double)f;
System.out.printf("%20.18f\n", f); // 9.123456954956055000
System.out.printf("%20.18f\n", d); // 9.123456700000000000
System.out.printf("%20.18f\n", d2);// 9.123456954956055000
}
}
이 경우에도 데이터 손실에 유의하자
class Casting{
public static void main(String[] args){
int i = 91234567;
float f = (float)i; //91234568.0000000
double d = (double)i; //91234567.0000000
//float의 정밀도는 최대 7자리 이므로, 8자리 이상의 정수를 변환하면 오차가 발생 할 수 있으므로 이 경우는 double을 권장한다.
float f2 = 1.666f;
int i2 = (int)f2; // 1
}
}
형변환을 생략하는 경우, 컴파일러가 자동적으로 수행한다.
서로 다른 두 타입간의 덧셈에서는 데이터손실을 고려하여 더 넓은 타입으로 변환한다.
byte
->short
,char
->int
->long
->float
->double
byte의 크기 순이지만, 실수형이 정수형보다 더 표현하는 방식이 넓기 때문에
float
이long
보다 우선적으로 변환된다.
short
와char
의 크기는 같지만 범위가 달라 양방향 모두 데이터 손실이 발생하기 때문에 자동 형변환 되지 않는다.
float f = 1234; //1234.0
//float f = (float)1234;
byte b = 1000; //ERROR
//큰 타입에서 작은 타입으로의 자동 형변환은 이루어 지지 않는다
byte b = (byte)1000; //-24
//명시할 경우 ERROR로 간주 하지 않음
int i = 3;
double d = 1.0 + i; //4.0
//double d = 1.0 + (double)i