Java는 백기선님의 유튜브를 통해 공부한다.
목표
자바의 프리미티브 타입, 변수 그리고 배열을 사용하는 방법을 익힙니다.
학습할 것
- 프리미티브 타입 종류와 값의 범위 그리고 기본 값
- 프리미티브 타입과 레퍼런스 타입
- 리터럴
- 변수 선언 및 초기화하는 방법
- 변수의 스코프와 라이프타임
- 타입 변환, 캐스팅 그리고 타입 프로모션
- 1차 및 2차 배열 선언하기
- 타입 추론, var
프리미티브 타입과 레퍼런스 타입
데이터에는 다양한 타입이 존재한다. 그 중 자바의 데이터값의 타입들은 다음과 같이 나눠진다.
자바 데이터타입 (ref 뇌를자극하는 Java 프로그래밍 - 한빛미디어)
프리미티브 타입
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
타입 할당되는 메모리 크기 기본값 데이터의 표현 범위
논리형 boolean 1 byte false true, false
정수형 byte 1 byte 0 -128 ~ 127
short 2 byte 0 -32,768 ~ 32,767
int(기본) 4 byte 0 -2,147,483,648
~ 2,147,483,647
long 8 byte 0L -9,223,372,036,854,775,808
~ 9,223,372,036,854,775,807
실수형 float 4 byte 0.0F (3.4 X 10-38) ~ (3.4 X 1038)
의 근사값
double(기본) 8 byte 0.0 (1.7 X 10-308) ~ (1.7 X 10308)
의 근사값
문자형 char 2 byte (유니코드) '\u0000' 0 ~ 65,535
- 특징
- 자바 언어에 내장된 기본 유형으로 기본형 타입(primitive type)을 미리 정의하여 제공
- 기본값이 있기 때문에 Null이 존재하지 않음
- 실제 값을 저장하는 공간으로 stack 메모리에 저장
- wrapper class는 각 privitive type을 클래스로 만든것
레퍼런스타입
1
2
3
4
5
6
7
8
9
10
11
12
타입 예시 기본값 할당되는 메모리 크기
배열 int[] arr = new int[5]; Null 4Byte (객체의 주소값)
열거 Null ''
클래스 String str = "test"; Null ''
Student sujin = new Student(); Null ''
인터페이스 Null ''
- 특징
- 기본형(primitive) 타입을 제외한 타입들이 모두 참조형 타입이다.
- 빈 객체를 의미하는 Null 존재
- 값이 저장되어 있는 곳의 주소값을 저장하는 공간으로 힙(Heap) 메모리에 저장
리터럴
- 변수(variable) : 하나의 값을 저장하기 위한 공간
- 상수(constant) : 값을 한번만 저장할 수 있는 공간
- 리터럴(literal) : 그 자체로 값을 의미하는 것
1
2
3
4
5
6
7
8
9
10
int year = 2017 ;
final int MAX_VALUE = 100 ;
----------------------------------------------
변수 : year
상수 : MAX_VALUE
리터럴 : 2017, 100
변수
- 변수
- 단 하나의 값을 저장할 수 있는 메모리 공간을 의미한다.
- 변수의 선언
- 변수에 저장될 값의 타입을 지정하고 변수에 이름을 붙여주는 것을 의미한다.
1
ex) int score ; // 정수형 타입의 score 변수를 선언
- 변수에 저장될 값의 타입을 지정하고 변수에 이름을 붙여주는 것을 의미한다.
- 변수의 초기화
- 변수를 사용하기 전에 처음으로 값을 저장하는 것을 의미한다
1
ex) int score = 100 ; // 정수형 타입의 score 변수를 선언하고, 100으로 초기화
- 변수를 사용하기 전에 처음으로 값을 저장하는 것을 의미한다
변수 명명 규칙
- 대소문자가 구분되며 길이에 제한이 없다.
1
max ≠ Max
- 숫자가 맨 앞에 올 수 없다.
1
main1( o ) 1main ( x )
- 특수문자는 _ 와 $만을 허용하며, 중간에 공백문자도 허용되지 않는다.
1
$harp( o ) S#arp( x ) apple_tree( o )
- 키워드는 사용할 수 없다.
1
true( x ) True( o )
- 대소문자가 구분되며 길이에 제한이 없다.
스코프와 라이프타임
변수와 메서드 같은 것들을 사용할수 있는 것은 이름이 있기 때문이다.
프로그램이 커지면 여러가지 이유로 이름이 충돌하게 된다. 이를 해결하기 위해 고안된것이 Scope이다. 때문에 변수들은 사용 가능한 범위를 가진다. 그 범위를 변수의 스코프라고 한다. 라이프타임 Lifetime 은 수명이라고 생각하면된다.
1
2
3
4
5
6
7
8
public class test {
int iv; // 인스턴스 변수
static int cv; // 클래스 변수
void method() {
int lv; // 지역 변수
}
}
- 인스턴스 변수(Instance Variables)
- 스코프scope : 클래스 전체(static제외)
- 라이프타임 lifetime : 객체가 메모리에 머무를때 까지
- 클래스 변수(Class Variables)
- 스코프scope : 클래스 전체
- 라이프타임 lifetime : 프로그램의 수명이 끝날때까지 또는 클래스가 메모리에 로드 되는 한
- 지역 변수(Local Variables)
- 스코프scope : 선언된 블록 내
- 라이프타임 lifetime : 선언된 블록을 벗어날때
형변환(캐스팅, casting)
형변환이란 변수 또는 상수의 타입을 다른 타입으로 변환하는 것을 말한다.
프로그램에서 값의 대입이나 연산을 수행할 때는 같은 타입끼리만 가능하다.
그래서 연산을 수행하기 전에 같은 타입으로 만들어야 하는데,
변수나 상수를 다른 타입으로 변환하는 것을 ‘형변환(casting)’ 이라고 한다.
타입을 그릇으로 보면 각 그릇의 크기가 다른데 그 안에 담기는 양도 재각기이다.
작은 그릇에 가득 차 있어도 큰 그릇에는 여유가 있지만 반대로, 큰 그릇에 가득 차 있으면 작은 그릇에 담을 때 넘칠 것이고,
큰 그릇에 적게 들어있으면 작은 그릇에도 담아질 것이다.
이처럼 작은 그릇에서 큰그릇은 문제가 없지만 큰그릇에서 작은그릇에 담을땐 주의해야한다.
형변환에서는 이런 경우, 자동 형변환과 강제 형변환이 있다.
자동형변환
형변환 구조 왼쪽에서 오른쪽으로는 자동 형변환이 가능하고, 반대는 강제로 형변환을 해주어야 한다.
1
2
int intValue = 1;
byte byteValue = (byte) intValue; <- 인트변수을 바이트에 대입함
- (byte)intValue; 변수앞에 강제형변환 타입을 ()안에 작성한다.
1차 및 2차 배열 선언하기
1차원 배열
배열은 같은 데이터 타입을 가진 연속된 메모리 공간으로 이루어진 자료구조이다.
같은 데이터 타입을 가진 여러개의 변수가 필요할 때 사용한다.
배열의 크기는 0이상의 정수값으로 정하며 [0,1,2,3,4,5,6’’‘]의 주소를 가진다. 배열은 Default 값을 갖게되는데 타입마다 다르다.
- 참조 타입 = null
- int , short , byte , long 타입 = 0
- float / double 타입 = 0.0
- bool 타입 = false
- char 타입 = \u0000
배열 생성
1
2
int[] array1 = new int[4];
타입[] 변수명 = new 타입[크기]; 크기가 4인 int타입의 배열을 생성하였다.
배열에 변수를 저장하는 방법
1
2
3
4
array1[0] = 1; 0부터 시작하여
array1[1] = 2; 0,1,2,3의 주소를 갖고 있다.
array1[2] = 3; <- 이렇게 주소에 변수를 저장할 수 있다.
array1[3] = 4;
변수를 사용하는 방법
- int value = array1[2]; <–array1 배열의 2번 주소의 변수를 value에 담는다.
- System.out.println(array1[1]); <– 배열의 1번 주소 변수를 출력한다.
선언과 동시에 초기화하는 방법
1
int[] array2 = new int[]{1,2,3,4,5};
2차원 배열
1차원 배열과 비슷하지만 1차원 배열들의 배열을 2차원 배열이라 할 수 있다.
예를 들면 다음과 같다.
1
2
3
4
5
int[][] array4 = new int[3][4]; // 1차원 배열을[3]개 구성하고 그 안에[4]개의 변수주소를 갖는다.
array4 -> 0 [0,0,0,0]
1 [0,0,0,0]
2 [0,0,0,0]
- 변수 저장 방법
- array4[0][0] = 10; //array4의 0번째 배열에 0번째 주소에 10을 저장한다.
- 가변크기의 2차원 배열을 생성하는 방법
1
int[][] array5 = new int[3][];
위와 같이 선언하면 array5는 3개짜리 배열을 만든다. 3개짜리 배열은 아직 변수를 저장하는 공간이 없다.
1 2 3
array5[0] = new int[2]; array5 의 0 번째 배열에 1개의 변수를 저장하는 공간을 만든다. array5[1] = new int[2]; array5 의 1 번째 배열에 2개의 변수를 저장하는 공간을 만든다. array5[2] = new int[3]; array5 의 2 번째 배열에 3개의 변수를 저장하는 공간을 만든다.
- 선언과 동시에 초기화하는 방법
.
타입추론(Type Inference) ‘var’
타입 추론이란 변수등을 초기화 또는 선언할때 타입을 정해주지 않아도 컴파일러가 코드를 초기화값을 보고 타입을 추론해 나가는 동작을 의미한다.
java 9까지는 generics와 lambda식에 대해 타입 추론을 지원하고 있었지만
Java 10에서 일반 타입의 타입추론을 위해 var라는 Local Variable Type-Inference 가 추가되었다
타입 추론의 기본
- String message = “Good bye, Java 9”; 가 기본이라면
- var message = “Hello, Java 10”; 처럼 타입 추론을 사용할 수 있다. 이 경우 var은 message의 타입을 String 으로 처리할 것이다.
var의 특징
- 지역변수로서만 선언 가능하다.
- 사용시 초기화값이 선언되어야 한다.
- 키워드가 아니다.
- 예를 들어 int는 함수나 변수의 이름이 불가하지만 var는 이름으로 사용 가능
- 사용시 런타임 오버 헤드 가 없으며 Java를 동적 유형 언어로 만들지 않는다.
var 유의사항
선언시 초기화값을 지정해 줘야한다.
1
var n; // error: cannot use 'var' on variable without initializer
null값으로 초기화 할 수 없다.
1
var emptyList = null; // error: variable initializer is 'null'
Lambda 식에는 명시적인 대상 유형이 필요하므로 var를 사용할 수 없다.
1
var p = (String s) -> s.length() > 10; //error:lambda expression needs an explicit target-type
배열에 사용할 수 없다.
1
var arr = { 1, 2, 3 }; // error: array initializer needs an explicit target-type
따라서, 가독성이 떨어질 때 사용하는 것을 추천한다.