이차원 배열을 다른 함수로 넘기기..

sadrove의 이미지

a함수에서 이차원 배열을 b함수로 넘길 때 아래와 같이 했습니다...
컴파일러가 경고메시지를 주던데..
이중포인터로 받아도 마찬가지고..
어떤식으로 넘겨야 하나요..?..^^..
도움 부탁드립니다.

void a(){
	char test[3][3];
	--- 생략 ---
	b(test);
}

void b(char *test){
	--- 생략 ---
}
kihongss의 이미지

sadrove wrote:
a함수에서 이차원 배열을 b함수로 넘길 때 아래와 같이 했습니다...
컴파일러가 경고메시지를 주던데..
이중포인터로 받아도 마찬가지고..
어떤식으로 넘겨야 하나요..?..^^..
도움 부탁드립니다.
void a(){
	char test[3][3];
	--- 생략 ---
	b(test);
}

void b(char *test){
	--- 생략 ---
}

void b(char test[][3]); 도 됩니다.


void a(){
	char test[3][3];
	--- 생략 ---
	b(test);
}

void b(char test[3][3]){
	--- 생략 ---
}
Fe.head의 이미지

#include <stdio.h>

void b(const int row, const int col, char * test)
{
    int i;
    for(i = 0 ; i<row; ++i)
    {
        printf("%s\n", test + i*col);
    }
}

int main()
{
    char    test[3][4] = {"abc", "cdz", "efz"};

    b(3, 4, (char *)test);

    return 0;
}

음. 했긴 했는데.
왜 b함수에서 char * test로 받는지 이유를 잘 모르겠군요.

#include <stdio.h>

void b(char (* const test)[4])
{
    int i;
    for(i = 0 ; i<3; ++i)
    {
        printf("%s\n", test[i]);
    }
}

int main()
{
    char    test[3][4] = {"abc", "cdz", "efz"};

    b(test);

    return 0;
}

고작 블로킹 하나, 고작 25점 중에 1점, 고작 부활동
"만약 그 순간이 온다면 그때가 네가 배구에 빠지는 순간이야"

Fe.head의 이미지

int main()
{
 80483db:   55                      push   %ebp
 80483dc:   89 e5                   mov    %esp,%ebp
 80483de:   83 ec 28                sub    $0x28,%esp
 80483e1:   83 e4 f0                and    $0xfffffff0,%esp
 80483e4:   b8 00 00 00 00          mov    $0x0,%eax
 80483e9:   29 c4                   sub    %eax,%esp
    char    test[3][4] = {"abc", "cdz", "efz"};
 80483eb:   a1 98 85 04 08          mov    0x8048598,%eax
 80483f0:   89 45 e8                mov    %eax,0xffffffe8(%ebp)
 80483f3:   a1 9c 85 04 08          mov    0x804859c,%eax
 80483f8:   89 45 ec                mov    %eax,0xffffffec(%ebp)
 80483fb:   a1 a0 85 04 08          mov    0x80485a0,%eax
 8048400:   89 45 f0                mov    %eax,0xfffffff0(%ebp)

2차원 배열이라구 해도 1차원 포인터로 할당 되는군요.
이거 gcc 에만 해당 되는지 아는분^^

고작 블로킹 하나, 고작 25점 중에 1점, 고작 부활동
"만약 그 순간이 온다면 그때가 네가 배구에 빠지는 순간이야"

doldori의 이미지

fehead wrote:
2차원 배열이라구 해도 1차원 포인터로 할당 되는군요.
이거 gcc 에만 해당 되는지 아는분^^

배열의 특징이 원래 그렇습니다. test[0][0]부터 test[2][3]이 연속적으로 배치되지요.
이 특징을 이용해서 다차원 배열을 1차원 포인터(?)로 넘기는 방법을 쓰기도 합니다.
htna의 이미지

int test[2][3];
과 같은 변수의 할당은 compile time에 어레이의 크기와 index가 결정됩니다.
그렇기에 이와같은 변수의 할당이나 함수의파라메터로의 전달은 1차원 이상의 고차원 배열에서 1차원의 어레이로 관리가 됩니다.

하지만, 동적크기의 어레이의 경우에는 compile time에 그 index가 결정될 수 없기 때문에.. "int test[2][3];"와 같은 방법으로 관리되지 않습니다.

WOW Wow!!!
Computer Science is no more about computers than astronomy is about telescopes.
-- E. W. Dijkstra

philossh의 이미지

void b(char (*test)[4]){...}

void a(){
     char test[3][4];
     ...
     b(test);
}

아니면 이런것도..

void b(char * test){...}

void a(){
    char test[3][4];
    ...
    b(test[0]);
    b(&test[0][0]);      //이것들은 다 똑같은건가.. --;
    b((char *)test);
}

To be or not to be.
That is the question.

tinywolf의 이미지

네 윗분들이 다 말씀해 주셨는데요..
한가지 첨언하자면..

가장 처음의 인덱스만 생략할 수 있습니다..
예를들면..

int a[5];
void func(int[] v);

int b[3][4];
void func(int[][4] v);

int c[7][8][9];
void func(int[][8][9] v);

이런 식으로..

왜냐하면 우선 단 하나의 포인터만으로 배열이 전달되는데요..
v[2][3] = 3;
과 같은 식으로 사용을 하려면 컴파일러가 (2,3)라는 위치가
(0,0)에서 얼마나 떨어진 것이지 알아야 컴파일이 가능하기 때문이지요..

그러니까 함수 머리에서 int[][4]와 같은 식으로
인덱스의 크기가 주어져야
'(2,3)번째 원소는 처음에서 (2*4+3)만큼 떨어져있다'
라고 계산할 수 있는 것입니다.
(row major, column major에 관한 내용도 보시면 좋습니다.)

대신 가장 처음의 인덱스는 없더라도 계산이 가능하기 때문에 생략할 수 있는 것입니다.
하지만 c는 boundary check(경계 검사)를 하지 않기 때문에..
주어진 배열의 크기는 int[3][4]라 하더라도
(6,3)에 접근할 수 있게 됩니다!!
(즉, 뒷부분 인덱스만 범위가 맞다면 가장앞 인덱스는 신경 쓰지 않죠!)
물론 이것은 논리적인 오류이지요.

만약 고정된 크기의 다차원 배열을 사용하신다면..
함수에 넘길 때에도

int a[5];
void func(int[5] v);

int b[3][4];
void func(int[3][4] v);

int c[7][8][9];
void func(int[7][8][9] v);

위와 같이 모든 인덱스를 다 써주시는 것을 추천드립니다.

그러면 컴파일러의 능력에 따라서 최대한 성의것 오류를 알려주겠지요..

ㅡ_ㅡ;

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.