자바 데이터 타입, 변수 그리고 배열

zwundzwzig·2023년 10월 7일
0

Java

목록 보기
9/9
post-thumbnail

자바부터 다시 하자.
백기선님의 자바 스터디 2020

Primitive Type

종류기본값범위크기
byte0-128 ~ 1271 byte(8 bit)
short0-32,768 ~ 32,7672 byte(16 bit)
int0-2,147,483,648 ~ 2,147,483,6474 byte(32 bit)
long0L-9,223,372,036,854,775,808 ~ 9,223,372,036,854,775,8078 byte(64 bit)
float0.0f(3.4 X 10-38) ~ (3.4 X 1038) 의 근사값4 byte(32 bit)
double0.0 || 0.0d(1.7 X 10-308) ~ (1.7 X 10308) 의 근사값8 byte(64 bit)
char'\u0000''\u0000' ~ '\uffff'(0 ~ 65,535)2 byte(16 bit)
booleanFALSEFALSE,TRUE1 byte(8 bit)

자바 기본형은 총 8개이고, 정수형(byte, short, int, log), 실수형(float, double), 문자형(char), 논리형(boolean)으로 구성돼 있다. null이 존재할 수 없다.

값이 할당될 때 변수의 주소 값에 값이 JVM의 Runtime Data Area 영역 중 Stack영역에 값이 저장된다.

Reference Type

class, interface, enum, array, String Type 등 기본형을 제외한 모든 타입이며, null이 존재한다.

값이 저장된 주소의 값을 저장한 변수가 JVM stack에 담기고 주소 값은 heap 영역에 담긴다.

Constant & Literal

상수는 변수처럼 값을 저장할 수 있는 공간이지만, 변수와 달리 한번 값을 저장하면 변경할 수 없다.

final int MAX_VALUE = 100; 
// `int MAX_VALUE`가 선언, `MAX_VALUE=100`가 초기화이다.
// 단순 선언 대신 초기화하자. 물론 jdk1.6부터 굳이 그러지 않아도 된다.
// 그래도 상수를 선언함과 동시에 초기화하는 습관을 들이자.

리터럴은 원시값과 같은 데이터 그 자체를 의미한다. 리터럴을 변수나 상수에 담는 것이다.

상수와의 차이는?
리터럴을 유동적으로 사용하기 위해선 변수나 상수 따위의 명칭으로 담아 사용하는 것이고,
상수는 리터럴 값을 변경하지 않고 사용하기 위해 쓰는 것이다.

변수의 초기화

선언한 변수에 초기값을 넣는 게 초기화이다. 멤버 변수는 초기화를 명시하지 않아도 변수의 타입에 맞는 기본값으로 초기화되지만 지역변수는 사용하기 전에 반드시 초기화가 이뤄져야 한다.

아래는 가장 기본적인 명시적 초기화 explict initialization 이다.

int x = 1000;
Football fb = new Football();

명시적 초기화만으로는 작업이 복잡한 경우 초기화 블럭을 사용한다.

static 키워드로 감싼 블럭이 클래스 초기화이고, 생성자를 사용하는 게 인스턴스 초기화 블럭이다.

이렇게 초기화된 클래스나 인스턴스는 각각 로딩되거나 생성될 때 처음 한 번 된다.

변수의 스코프와 생명주기 출처

인스턴스 변수

  • 클래스 내부와 모든 메소드 및 블록 외부에서 선언되는 변수는 인스턴스 변수
  • 스코프 :정적 메서드를 제외하고 클래스 전체에 적용
  • 생명주기 : 객체가 메모리에 남아 있을 때까지

클래스(static) 변수

  • 클래스 내부, 모든 블록 외부에서 선언되고 정적으로 표시된 변수
  • 스코프 : 클래스 전체
  • 생명주기 : 프로그램이 끝날 때까지 또는 클래스가 메모리에 로드되는 동안

로컬 변수

  • 인스턴스 및 클래스 변수가 아닌 다른 모든 변수. 메서드의 매개 변수 포함
  • 스코프 : 선언된 블록 내
  • 생명주기 : 컨트롤이 선언된 블록을 떠날 때까지

타입 변환, 캐스팅 그리고 타입 프로모션

  • Primitive type
    • Widening type cast: 더 넓은 타입으로의 형 변환
      • ex. int ➡️ long, byte ➡️ short ...
    • Narrow type cast: 더 좁은 타입으로의 형 변환
      • 🚫 값이 손실될 수 있음
      • ex. long ➡️ int, short ➡️ byte ...
  • Reference type
    • 상속Inheritance 관계에서만 가능
    • implicit up-casting : subclass → superclass
      • 모든 subclass 는 superclass 의 속성을 갖고 있어 superclass 로의 casting 가능
      • LSP
    • explicit down-casting: superclass → subclass
      • 모든 superclass 는 subclass 의 속성을 갖지 않을 수 있음 ➡️ 오류 발생 가능성 존재

1차 및 2차 배열 선언하기

class ArrayExample {
	public static void main(String[] args) {
        //1차원 배열
        int[] oneDimensionArrayEx1 = {1, 2, 3, 4, 5};
        int[] oneDimensionArrayEx2;
        oneDimensionArrayEx2 = new int[10];

        //2차원 배열
        int[][] twoDimensionArrayEx1 = {{1, 2}, {3, 4}};
        int[][] twoDimensionArrayEx2;
        twoDimensionArrayEx2 = new int[10][10];
    }
}
  • 1차원 배열
    • 위 oneDimensionArrayEx1 은 Runtime Stack 영역 내 Heap Area의 주소값을 가짐
    • Heap 영역에 int 타입 크기의 요소 5개를 할당해 사용
  • 2차원 배열
    • Runtime Stack 영역의 twoDimensionArrayEx1 은 2개의 요소 크기(2개 요소 주소값을 가지고 있음)를 가진 힙 영역 주소값을 가짐
    • 힙 영역에는 실제 값이 들어있는 요소들과 주소값이 들어있는 요소들로 존재하게됨

Type Inference, var

타입 추론이란?
데이터 타입을 소스코드에 명시하지 않더라도, 컴파일 단계에서 컴파일러가 method 호출 및 선언과 variable 혹은 object 선언을 활용해 실제 타입을 추론하여 값을 할당하는 것

  • Generic type
    • C++ 의 template 과 비슷한 개념으로 보임
    • 그러나 Generic 은 primitive type 사용 불가
    • template 과는 다르게 type-erasure 개념이 적용되어 type safe를 최대한 보장하려고 노력함
      • type-erasure: 컴파일러가 parameterized type에서는 새로운 클래스들이 생성되지 않는 걸 보장함
        • 컴파일러가 unbound type T 를 Object 로 변환함
          public static <T> boolean hasElement(T[] elements, T element){
          	for(T e : elements){
          		if(e.equals(element){
          			return true;
          		}
          	}
          	return false;
          }
          ⬇️
          public static boolean hasElement(Object[] elements, Object element){
          	for(Object e : elements){
          		if(e.equals(element){
          			return true;
          		}
          	}
          	return false;
          }
          Ref. https://www.baeldung.com/java-type-erasure
      • 결국 생성된 바이트코드에는 원래의 class, interface, method 만을 포함하고 있음

1.5 버전 부터 추가된 Generic 이나 1.8 버전에서 추가된 lamda 에서 타입추론이 사용된다. 그리고 1.10 버전 에서는 이러한 타입추론을 사용하는 var 이라는 Local Variable Type-Inference 추가

출처
profile
개발이란?

0개의 댓글