C 언어 동적 배열 - C eon-eo dongjeog baeyeol

2차원 배열 동적할당

2차원 배열을 동적 할당하기 위해선 조금 다른 방법을 사용해야 한다.

1. 배열 포인터를 사용하여 동적 할당 하는 방법

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

#include <stdio.h>

#include <stdlib.h>

//2차원 배열 동적 메모리 할당 

int main()

{

int (*ptr)[3]; //동적 메모리 공간을 할당 받기 위한 포인터 배열

int i,n,j;

printf("몇행을 할당 하시겠습니까? ");

scanf("%d",&n); 

ptr = (int(*)[3])malloc(sizeof(int* 3 * n);  // 2차원 배열을 처리하기 위해 수식 표현

if(ptr == NULL// 동적할당 실패시 NULL 리턴

{

printf("동적 할당 실패"); 

}

for(i;i<n;i++)

{

for(j=0;j<3;j++)

{

ptr[i][j]=i;    

printf("%d",ptr[i][j]);    

}    

printf("\n"); 

free(ptr);

실행결과

몇행을 할당 하시겠습니까? 5

000

111

222

333

444

 

2. 이중 포인터를 사용한 동적 할당 방법

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

#include <stdio.h>

#include <stdlib.h>

int main()

{

int n=3//행 

int m=4//열 

int i,j;

int** p;

= (int**)malloc(sizeof(int** n); //행을 의미한다 

if(p == NULLprintf("동적할당 실패");

for(i=0;i<n;i++)

{

p[i] = (int*)malloc(sizeof(int* m); //열을 의미한다 

}    

for(i=0;i<n;i++)

{

for(j=0;j<m;j++)

{

p[i][j] = j+10;

}

}

for(i=0;i<n;i++)

{

for(j=0;j<m;j++)

{

printf("%d",p[i][j]);

}

printf("\n");

}

for(i=0; i<n; i++)

{

free(p[i]);

}

free(p);

}

실행결과

[10][11][12][13]

[10][11][12][13]

[10][11][12][13]

 

위의 이중 포인터를 사용한 방법이 가장 일반적이다 그리고 위의 방법을 사용해야 동적할당을 하는 의미가 있다.

3. 이중 포인터를 사용한 동적 할당 포인터 변수 함수의 매개변수로 전달

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

#include<stdio.h>

#include<stdlib.h>

int height=6;

int width=8;

int sub(int*** arr); //삼중 포인터로 인자 받음 

int sub(int*** arr)  //Call By Reference이기 때문에 삼중 포인터를 사용한다.

{    

int i,j;

for(i=0; i<height; i++)

{

for(j=0; j<width; j++)

{

(*arr)[i][j] = i+10;

}

}

for(i=0; i<height; i++)

{

for(j=0; j<width; j++)

{

printf("%3d", (*arr)[i][j]);

}

printf("\n");

}                                                    

for(i=0; i<height; i++)

{

free((*arr)[i]);

}

free(*arr);

return 0;

}

int main(void)

{

int **arr;

int i,j;

arr=(int**)malloc(sizeof(int*)*height); //행을 만든다고 생각하자

for(i=0; i<height; i++)

{

arr[i] = (int*)malloc(sizeof(int)*width); //열을 만든다고 생각하자

}

sub(&arr);

return 0;

}

 

이중 포인터를 사용하였기 때문에 함수의 형식매개변수 에서 전달 받을때에는 ***삼중 포인터를 사용해야 한다 (Call By Reference 방식일경우)

(Call By Value) 일 경우에는 **이중 포인터를 사용하여 받을수 있다.

= (int**)malloc(sizeof(int** n); //2차원 배열 동적할당 -> 행을 의미한다고 할수 있다. for(i=0;i<n;i++) { p[i] = (int*)malloc(sizeof(int) * m); //열을 의미한다 }

 

사실 위의 코드가 이해하기 힘들다 이중 포인터를 왜 써야 할까 라는 생각이 들수 있다 기존에 우리가 1차원 배열을 동적할당 할 때에는

= (int()malloc(sizeof(int* n); //1차원 배열 동적할당

 

위와 같은 형태를 사용하였다 이 말은 4byte공간 n개를 만들겠다는 뜻이다. 하지만 2차원 배열은 행과,열이라는 표기로 나누게 된다

C 언어 동적 배열 - C eon-eo dongjeog baeyeol

즉, 2차원 배열은 int의 주소를 넘겨주는것이다 sizeof(int*) 뜻은 포인터 변수의 주소를 n개 만들겠다는 뜻이다.

그래서 int의 공간 n개를 만들고 거기의 시작주소를 넘겨주기 때문에 **p 이중포인터로 받는것이다.

그리고 n개의 int공간을 만들고 해당 주소를 넘겨 받으면 또 그 공간에 우리가 부르는 '열' 이라는 공간을 만드는것이다.

그림을 잘 그리진 못했지만 위와 같은 형태라고 생각하면 이해가 편할것이다. 각 문법이 의미하는 것을 도식화 하였다.