오늘은 참조 타입 중, 배열 타입에 대해서 알아보려고 한다.
배열(
array
)이란 같은 타입의 변수를 연속된 공간에 나열시키고, 각 데이터에 인덱스를 부여해 놓은 자료구조이다.
element
): 배열을 구성하는 각각의 값index
): 배열에서의 위치를 가리키는 숫자배열은 같은 타입의 많은 양의 데이터를 다룰 때 효율적으로 사용할 수 있도록 하는 자료구조이다.
Type mismatch
) 컴파일 오류가 발생한다.배열을 선언하는 방법은 다음과 같다.
1. 타입[] 배열이름; 2. 타입 배열이름[];
//첫 번째 방법
int[] intArray;
double[] doubleArray;
String[] strArray;
//두 번째 방법
int intArray[];
double doubleArray[];
String strArray[];
배열 항목에 저장될 값의 목록을 가지고 있다면, 다음과 같이 배열 객체를 만들 수 있다.
데이터타입[] 배열이름 = { 값0, 값1, 값2, ... };
중괄호 {}
는 주어진 값들을 항목으로 가지는 배열 객체를 힙에 생성하고, 배열 객체의 번지를 리턴한다. 배열 변수는 리턴된 번지를 저장함으로써 참조가 이뤄진다.
📌 값의 목록으로 배열 객체를 생성할 때 주의할 점!
배열 변수를 이미 선언한 후에 다른 실행문에서 중괄호를 사용한 배열 생성은 허용되지 않는다.
타입[] 변수;
변수 = { 값0, 값1, 값2, ... }; //컴파일 에러
이렇게 배열 변수를 미리 선언한 경우, new
연산자를 이용하여 배열을 생성해야 한다. (아래에서 살펴볼 것)
new
연산자로 배열 생성지금 당장은 값의 목록은 가지고 있지 않지만, 앞으로 사용할 예정인 배열을 미리 만들고 싶다면
new
연산자로 배열 객체를 생성할 수 있다.
타입[] 배열이름 = new 타입[배열길이];
new
연산자로 배열을 생성할 경우에는 이미 배열 변수가 선언된 후에도 가능하다.
타입[] 배열이름 = null;
배열이름 = new 타입[배열길이];
int[] intArray = new int[5];
위의 코드는 길이가 5인 int[]
배열을 생성한다.
new
연산자로 배열을 처음 생성할 경우, 배열은 자동적으로 기본값으로 초기화된다.
intArray
는 int
타입 배열이므로 intArray[0]
부터 intArray[4]
까지 모두 기본값 0으로 초기화된다.
만약 String
배열을 생성했다면 모두 null
값으로 초기화된다.
String[] strArray = new String[5];
배열이 생성되고 나서 새로운 값을 저장하려면 대입 연산자를 이용하면 된다.
배열이름[인덱스] = 값;
int[] scores = new int[3];
scores[0] = 83;
scores[1] = 49;
scores[2] = 72;
배열의 길이란 배열에 저장할 수 잇는 전체 항목 수를 말한다.
코드에서 배열의 길이를 얻으려면 배열 객체의length
필드를 읽으면 된다.
배열변수.length;
int[] intArray = {10, 20, 30};
int num = intArray.length(); //num 값은 3
length
는 읽기 전용 필드이기 때문에, 값을 바꿀 수 없다.
다차원 배열은 2차원 이상의 배열을 의미하며, 배열 요소로 또 다른 배열을 가지는 배열을 의미한다.
2차원 배열은 배열의 요소로 1차원 배열을 가지는 배열
2차원 배열을 선언하는 방법은 다음과 같다.
1. 타입[][] 배열이름;
2. 타입 배열이름[][];
3. 타입[] 배열이름[];
2차원 배열을 도식적으로 표현하면 다음과 같다.
int[][] arr = new int[2][3];
배열 arr
의 length
를 구해보면 다음과 같다.
arr.length //2 (배열 arr의 길이)
arr[0].length //3 (배열 B의 길이)
arr[1].length //3 (배열 C의 길이)
기본 타입 배열은 각 항목에 직접 값을 갖고 있지만,
참조 타입 (클래스, 인터페이스) 배열은 각 항목에 객체의 번지를 가지고 있다.
예를 들어, String
은 클래스 타입이므로 String[]
배열은 각 항목에 문자열이 아니라, String
객체의 주소를 가지고 있다. 즉, String
객체를 참조하게 된다.
String[] strArray = new String[3];
strArray[0] = "Java";
strArray[1] = "C++";
strArray[2] = "C#";
위의 코드는 배열 strArray
를 선언하고 3개의 문자열을 참조하는 배열을 생성한다.
그림으로 표현하면 다음과 같다.
따라서 String[]
배열의 항목도 결국 String
변수와 동일하게 취급되어야 한다.
예를 들어 배열 항목 간에 문자열 비교할 때 ==
연산자 대신 equals()
메소드를 사용해야 한다.
==
는 객체의 번지 비교이기 때문에 문자열 비교에 사용할 수 없다.
위에서 "한 번 생성된 배열은 길이를 늘리거나 줄일 수 없다."라고 했다.
그렇기 때문에 더 많은 저장 공간이 필요하다면 더 큰 배열을 새로 만들고 이전 배열로부터 항목 값들을 복사해야 한다.
📌 배열 간의 항목 값들을 복사하려면
- for문을 사용하거나,
System.arraycopy()
메소드를 사용하면 된다.
for
문으로 배열을 복사하는 방법public class ArrayCopyByForExample {
public static void main(String[] args) {
int[] oldIntArray = {1, 2, 3};
int[] newIntArray = new int[5];
for (int i = 0; i < oldIntArray.length; i++) {
newIntArray[i] = oldIntArray[i];
}
for (int i = 0; i < newIntArray.length; i++) {
System.out.print(newIntArray[i] + ", ");
}
}
}
1, 2, 3, 0, 0,
위 코드는 다음과 같이 배열을 복사시킨다.
복사되지 않은 항목은 int[]
배열의 기본 초기값 0
이 그대로 유지된다.
System.arraycopy()
메소드를 이용하여 배열을 복사하는 방법📌
System.arraycopy()
를 호출하는 방법
System.arraycopy(Object src, int srcPos, Object dest, int destPos, int length);
src
: 원본 배열srcPos
: 원본 배열에서 복사할 항목의 시작 인덱스dest
: 새 배열destPos
: 새 배열에서 붙여넣을 시작 인덱스length
: 복사할 개수public class ArrayCopyByExample {
public static void main(String[] args) {
String[] oldStrArray = {"java", "array", "copy"};
String[] newStrArray = new String[5];
System.arraycopy(oldStrArray, 0, newStrArray, 0, oldStrArray.length);
for (int i = 0; i < newStrArray.length; i++) {
System.out.print(newStrArray[i] + ", ");
}
}
}
java, array, copy, null, null,
위 코드는 다음과 같이 배열을 복사시킨다.
복사되지 않은 항목은 String[]
배열의 기본 초기값인 null
이 그대로 유지된다.
참조 타입 배열일 경우, 배열 복사가 되면 복사되는 값이 객체의 번지이므로 새 배열의 항목은 이전 배열의 항목이 참조하는 객체와 동일하다. 이것을 얕은 복사(shallow copy
)라고 한다.
(↔ 깊은 복사(deep copy
)는 참조한느 객체도 별도로 생성하는 것을 말한다.)
for
문 ( Enhanced for
문 )JDK 1.5부터 배열과 컬렉션의 모든 요소를 참조하기 위한
Enhanced for
문이라는 향상된 for문을 제공한다. 향상된 for문은 반복 실행을 하기 위해 카운터 변수와 증감식을 사용하지 않는다. 배열 및 컬렉션 항목의 개수만큼 반복하고, 자동적으로 for문을 빠져 나간다.
문법은 다음과 같다.
for (타입 변수이름: 배열이나컬렉션이름) {
배열의 길이만큼 반복적으로 실행하고자 하는 명령문;
}
public class EnhancedForExample {
public static void main(String[] args) {
int[] scores = new int[]{59, 91, 74, 66, 28};
for (int score : scores) {
System.out.print(score + " ");
}
}
}
59 91 74 66 28