본문 바로가기

공부/C언어

C언어 - (13) : 다차원 배열

'다차원 배열'이란 말 그대로 2차원 이상의 배열을 의미한다

 

1차원 배열을 `int arr[10];`과 같은 방식으로 선언했다면, `int arr_2d[5][5];`와 같은 방식으로 5x5의 2차원 배열을 선언할 수 있고

`int arr_3d[3][3][3];`과 같이 3x3x3의 3차원 배열과 그 이상도 선언할 수 있다.

 

배열의 원소에 대한 접근 방법 역시 1차원 배열의 접근 방식과 동일하며, 차원 수에 맞는 index를 넣어주는 것만 신경써주면 된다

#include <stdio.h>
int main(void)
{
    int villa[4][2];
    int popu, i, j;
    // 가구별 거주인원 입력 받기
    for (i=0; i<4; i++)
    {
        for (j=0; j<2; j++)
        {
            printf("%d층 %d호 인구수: ", i+1, j+1);
            scanf("%d", &villa[i][j]);
        }
    }

    // 층별 인구수 출력하기
    for (i=0; i<4; i++)
    {
        popu=0;
        popu+=(villa[i][0]+villa[i][1]);
        printf("%d층 인구수: %d \n", i+1, popu);
    }
    
    return 0;
}

위 코드를 통해 2차원 배열을 어떻게 사용하는지에 대해 어느 정도 감을 익힐 수 있다.

2차원 배열의 메모리 할당

2차원 배열의 메모리 할당 방식 역시 1차원 배열의 그것과 유사하다.

3x2인 `arr[3][2]`배열이 있다면, 다음과 같은 방식으로 메모리가 할당된다.

  1. 첫번째 차원의 첫 원소`arr[0]`
    • 두번째 차원의 첫 원소부터 마지막 원소까지 : `arr[0][0], arr[0][1]`
  2. 반복

따라서, 다음과 같은 소스 코드를 실행시키면 배열의 자료형 크기 만큼 주소값이 순차적으로 늘어나는 결과값을 확인할 수 있다.

#include <stdio.h>
int main(void)
{
    int arr[3][2];
    int i,j;
    for (i=0; i<3; i++)
    {
        for (j=0; j<2; j++)
            printf("%p \n", &arr[i][j]);
    }

    return 0;
}

2차원 배열의 선언 + 초기화

2차원 배열을 선언과 동시에 초기화하는 방법은 다음과 같다.

// 첫번째(중괄호 명시)
int arr[3][3] = {
    {1,0,0},
    {4,5,0},
    {7,8,9}
};

// 두번째(중괄호 명시 X)
int arr[3][3] = {
    1,0,0,
    4,5,0,
    7,8,9
};

// 세번째(한줄로 초기화)
int arr[3][3] = {1,2,3,4,5,6,7,8,9};

위와 같이 다양한 방법으로 선언과 동시에 초기화가 가능하고, 채워지지 않은 부분에 대해서는 공통적으로 0으로 초기화된다.

2차원 배열의 크기 선언

1차원 배열의 경우에는 `int arr[] = {1,2,3};`과 같이 선언+초기화를 해도 컴파일러에서 자동으로 '3'의 크기로 채워줄 수 있었다. 

 

하지만, 2차원 배열의 경우에는 `int arr[][] = {1,2,3,4,5,6};`으로 선언+초기화를 하게 되면 2차원 배열의 크기가 2x3인지 3x2인지 알수가 없다. 따라서 두 차원의 크기를 모두 명시해주는 것이 가장 확실하겠지만, 세로(두번째) 차원 크기는 명시해주어야 한다.

int arr[][] = {1,2,3,4,5,6}; // ERROR
int arr[2][] = {1,2,3,4,5,6}; // ERROR
int arr[][3] = {1,2,3,4,5,6}; // OK