배열
1. 배열
7월 한 달 동안의 일별 최고 기온을 저장할 때 → 7월은 총 31일 → 총 31개의 변수가 필요합니다.
매우 비효율적입니다.
배열이란, 동일한 타입의 값들을 하나의 묶음으로 묶은 자료 구조를 의미합니다.
배열을 사용하여 값을 저장하는 경우, 연속적으로 값들이 모여서 저장됩니다.
배열을 초기화하지 않을 경우 요소는 null입니다.
double[] temperatureOfJuly = { 27.4, 30.1, ..., 31.8 };
2. 1차원 배열
1차원 배열을 선언할 때에는 다음과 같이 타입 뒤에 대괄호를 붙여서 선언하고 초기화할 수 있습니다.
double[] temperatureOfJuly; // 배열을 가리킬 참조 변수 temperatureOfJuly를 선언합니다.
temperatureOfJuly = new double[31]; // double형의 기본값인 0.0으로 초기화, 총 31개의 double형 값을 저장할 수 있는 배열이 생성됩니다.
// 대입 연산자(=)에 의해 생성된 배열 첫 번째 요소의 주소값이 참조 변수 temperatureOfJuly에 할당됩니다.
자바에서 배열은 참조 타입에 해당합니다.
따라서 double[]이라는 배열 선언 문법으로 선언한 temperatureOfJuly는 선언 이후에 생성될 배열의 주소값을 담을 참조 변수가 됩니다.
-
기본 타입의 값을 변수에 할당하면 해당 변수에는 실제 값이 저장됩니다.
int형, double형과 같은 기본 타입의 경우, 기본 타입의 값을 저장할 변수를 선언하는 시점에 얼마만큼의 메모리 공간을 확보해야 하는지 컴퓨터가 알 수 있습니다.
변수 이름 앞에 타입이 붙어 있으며, 각 타입 별로 크기가 정해져 있기 때문입니다. -
참조 타입의 값을 변수에 할당하면 해당 변수에는 주소값이 저장됩니다.
double[] temperatureOfJuly;와 같이 배열을 선언하는 시점에 배열이 몇 개의 요소를 가질지 컴퓨터는 알 수 없습니다.
따라서 배열을 선언하면, 이후에 생성될 배열의 주소값을 담을 메모리 공간만이 확보됩니다.
이후 배열이 생성되고 난 다음에 해당 배열의 시작 주소값이 참조 변수에 할당됩니다.
첫 번째 요소는 temperatureOfJuly[0]으로 접근할 수 있습니다. 세 번째 요소는 temperatureOfJuly[2]로 접근할 수 있습니다.
double[] temperatureOfJuly = new double[31];
System.out.println(temperatureOfJuly.length); // 31
배열이 가진 요소의 개수를 배열의 길이 또는 크기라고 합니다. 배열의 길이는 배열_참조_변수_이름.length로 얻을 수 있습니다.
2. 2차원 배열
int[][] kcal;
kcal = new int[31][3];
int[][] kcal = new int[31][3];
{
{ 0, 0, 0 },
{ 0, 0, 0 },
{ 0, 0, 0 },
...
{ 0, 0, 0 }
}
3. 가변 배열
배열이 2차원 이상일 때, 마지막 차수에 해당하는 배열의 길이를 고정하지 않아도 되며, 이러한 배열을 가변 배열이라고 합니다.
int[][] ages = new int[5][];
int[][] ages = new int[5][];
ages[0] = new int[5];
ages[1] = new int[6];
ages[2] = new int[7];
ages[3] = new int[8];
ages[4] = new int[9];
System.out.println("Arrays.toString(ages[0]) = " + Arrays.toString(ages[0]));
System.out.println("Arrays.toString(ages[1]) = " + Arrays.toString(ages[1]));
System.out.println("Arrays.toString(ages[2]) = " + Arrays.toString(ages[2]));
System.out.println("Arrays.toString(ages[3]) = " + Arrays.toString(ages[3]));
System.out.println("Arrays.toString(ages[4]) = " + Arrays.toString(ages[4]));
// 결과
// Arrays.toString(ages[0]) = [0, 0, 0, 0, 0]
// Arrays.toString(ages[1]) = [0, 0, 0, 0, 0, 0]
// Arrays.toString(ages[2]) = [0, 0, 0, 0, 0, 0, 0]
// Arrays.toString(ages[3]) = [0, 0, 0, 0, 0, 0, 0, 0]
// Arrays.toString(ages[4]) = [0, 0, 0, 0, 0, 0, 0, 0, 0]
여기서 ages 배열의 길이는 5이므로 ages[5] = new int[10]; 을 만약에 추가하게 되면
배열의 길이가 6이 되므로 ArrayIndexOutOfBoundsException으로 예외가 발생합니다.
4. 배열 탐색
반복문을 통한 배열 탐색할 수 있습니다.
// for 문
int[] scores = { 100, 90, 85, 95, 100 };
int sum = 0;
for (int i = 0; i < scores.length; i++) {
sum += scores[i];
}
System.out.println(sum); // 470
// while 문
int[] scores = { 100, 90, 85, 95, 100 };
int sum = 0;
int i = 0;
while (i < scores.length) {
sum += scores[i++];
}
System.out.println(sum); // 470
//향상된 for 문
int[] scores = { 100, 90, 85, 95, 100 };
int sum = 0;
for (int score: scores) {
sum += score;
}
System.out.println(sum); // 470
- 주의사항
향상된 for 루프에서 요소의 값 자체를 수정하는 것은 원본 배열에는 영향을 주지 않습니다.
대신에 요소의 값이 복사되어 사용되므로 해당 반복문 내에서 요소 값을 수정하더라도 원본 배열에는 영향을 주지 않습니다.
아래 코드에서 배열의 각 요소를 2로 변경하고 있지만, 원본 배열에는 영향을 주지 않으므로 결과값은 변하지 않습니다.
바꿀 수 없는 이유는 향상된 for 루프에서 반복 변수인 score는 배열의 요소를 순회하는데 사용되는 임시 변수로서 역할합니다.
이 변수의 값은 배열의 각 요소의 값을 복사하여 가지고 있게 됩니다.
따라서 이 변수를 통해 배열의 요소를 변경하더라도 실제로는 임시 변수에 저장된 값만 변경되고, 원본 배열의 값은 변경되지 않습니다.
간단히 말해, 향상된 for 루프에서는 배열의 요소를 직접적으로 수정할 수 없습니다.
요소를 수정하려면 일반적인 for 루프를 사용하여 배열의 인덱스를 직접 조작해야 합니다.
int[] scores = { 100, 90, 85, 95, 100 };
// 일반적인 for문 및 while문을 사용하면 배열 요소의 값을 바꿀 수 있습니다.
for (int i = 0; i < scores.length; i++) {
scores[i] = 0;
}
System.out.println("for문 사용 : " + Arrays.toString(scores));
int j = 0;
while (j < scores.length) {
scores[j++] = 1;
}
System.out.println("while문 사용 : " + Arrays.toString(scores));
// 향상된 for문을 사용하면 배열 요소의 값을 바꿀 수 없습니다.
for (int score: scores) {
score = 2;
}
System.out.println("향상된 for문 사용 : " + Arrays.toString(scores));
/*
실행 결과
for문 사용 : [0, 0, 0, 0, 0]
while문 사용 : [1, 1, 1, 1, 1]
향상된 for문 사용 : [1, 1, 1, 1, 1] 위 while 문 값 그대로 출력되었습니다.
만약 배열 선언 후 향상된 for 문 만 사용하면 [100, 90, 85, 95, 100] 이 출력 될 것입니다.
*/