함수에서 포인터를 사용하는 경우는 보통 다음과 같은 세가지 경우가 있다고 한다.

1. 매개 변수가 포인터
출력을 매개변수에 저장해서 보내는 것이 아닐까 추측하면 대부분 맞음.

void Add(int a, int b, int *c) {
	*c = a + b;
}

2. 반환 값을 여러 개 받고 싶은 경우
C++에서는 보통 반환값을 하나 밖에 받지 못한다. (ex: return X;)
함수를 실행 시켰을때 반환 값을 여러개 받(는 것처럼 하)고 싶다면,

void Add(int a, int b, int *c, int *d) {
	*c = a + b;
	*d = a - b;
}

와 같이 활용할 수 있다.

3. 크기가 엄청 큰 배열을 함수로 넘겨줄 때

bool IsEqual(const char str1[], const char str2[])
{
    int i=0;
    while(i<kMaxStr) {
        for(int j=0; j<kMaxStr;j++) {
            
            if(str1[i]!=str2[i])
                return false;
            else
                return true;
            i++;
        }
    }
    return true;
}

int main()
{
    const char str1[kMaxStr] = "stop";
    while (1)
    {
        char str2[kMaxStr];
        cin >> str2;

        if(IsEqual(str1, str2)) 
        {
            cout << "종료합니다.\n";
            break;            
        } else
            cout<<"계속합니다.\n";
    }

    return 0;
}

위의 IsEqual함수의 매개변수는 사실 배열이 아니라 포인터이다. 배열이 시작하는 곳의 주소.
sizeof(str1), sizeof(str2)를 해보면 둘다 포인터기 때문에 8바이트가 나온다. (크기가 100인 배열이면 100바이트가 나와야함) 문자의 배열 두개를 넘겨주는 것처럼 호출을 하고 있으나 내부적으로는 포인터이고, 아예

bool IsEqual(const char *str1, const char *str2)


 처럼 만드는 것도 괜찮다.

 

3번이 잘 이해가 안가서 wrtn.ai에게 물어보았고 답변 결과는 다음과 같았다.

C++에서 배열을 함수의 매개변수로 사용할 때, 실제로는 포인터가 사용됩니다. 이를 이해하기 위해선 배열과 포인터의 관계, 그리고 C++에서의 배열 인자 처리 방식에 대해 자세히 살펴볼 필요가 있습니다.
1. 배열과 포인터의 관계
C++에서 배열 이름은 배열의 첫 번째 요소를 가리키는 포인터로 사용될 수 있습니다. 예를 들어, int arr[10];이라는 배열이 있다면, arr은 &arr[0]을 의미하는 포인터로 해석될 수 있습니다. 배열의 이름 자체가 배열의 첫 번째 원소를 가리키는 주소로 변환됩니다.
2. 함수에서의 배열 인자
함수에 배열을 인자로 넘길 때, 배열의 크기 정보는 전달되지 않습니다. 대신, 배열의 이름(즉, 배열의 첫 번째 요소를 가리키는 포인터)만이 함수에 전달됩니다. 따라서, IsEqual(const char str1[], const char str2[]) 함수 선언에서 str1과 str2는 사실상 const char* str1, const char* str2와 동일하게 처리됩니다. 여기서 const 키워드는 포인터가 가리키는 데이터를 변경할 수 없음을 의미합니다.
3. 함수 내 배열 접근
함수 내에서 이 포인터(즉, 배열 이름)를 사용하여 배열의 각 요소에 접근할 수 있습니다. 포인터 산술을 사용하거나 배열 인덱싱 문법을 사용하여 이를 수행할 수 있으며, 이는 내부적으로 포인터 산술로 처리됩니다.
4. 결론
따라서, IsEqual 함수에서 const char str1[], const char str2[]를 매개변수로 사용할 때, 이들은 실제로는 const char* 타입의 포인터로 처리되며, 이 포인터들은 각각 문자열 str1과 str2의 첫 번째 문자를 가리키게 됩니다. 이를 통해 함수 내에서 문자열의 각 문자에 접근하여 비교할 수 있는 것입니다.
간단히 말해서, const char str1[]와 같은 매개변수는 포인터이며, 이는 함수에 전달될 때 배열의 크기 정보 없이 배열의 시작 주소만을 전달하기 때문입니다. 이런 방식으로 배열을 함수에 전달하는 것은 C++에서 일반적인 배열 처리 방법입니다.

'게임 개발 > C++언어' 카테고리의 다른 글

Ch03. 클래스의 기본  (0) 2020.12.23
C++언어 포스팅 계획  (0) 2020.12.23

03-1. C++, 그리고 구조체

 

 우리는 C언어를 공부하며 구조체에 대한 학습을 했다. 관련된 데이터를 묶었을때, 프로그램의 구현 및 관리를 쉽게 할 수 있기에 구조체가 중요한 역할을 했다. 게임으로 쉽게 예를 들어보자. 다음은 유비소프트 사의 '레인보우 식스:시즈'에 등장하는 한 캐릭터이다.

주무기로 방패를 사용한다.

 이 캐릭터 하나를 구성하는 요소는 얼마나 될까? 생각나는대로만 적어보자면 움직임, 일반공격, 사격, 히트박스, 특수능력, 사운드, 총기 등이 있다. 그리고 이러한 캐릭터는 게임상에서 약 50가지 존재한다. 그렇다면 캐릭터마다 각각의 요소를 코딩하는 것은 상당히 비효율적이고, 힘들 것이다. 이를 위해 구조체가 등장한 것이다. 

 캐릭터들이 공통으로 가지고 있는 움직임, 사격, 일반 공격 등에 대해서 구조체를 사용해 코딩한다면, 더욱 간편한 사용이 가능할 것이다.  C언어 스타일로 구조체를 정의하자면 다음과 같다.

struct Operator
{
    char operName[OP_LEN]; //오퍼레이터(캐릭터) 이름, OP_LEN은 매크로 상수
    int hitboxHEAD; //머리에 입는 데미지
    int hitboxBODY; //몸에 입는 데미지
    int hitboxARMnLEG; //팔다리에 입는 데미지
    int HP; //체력
    int amour; //보호구
    int atkDMG; //사격데미지
    int melDMG; //근접공격데미지
    int sklDMG; //스킬데미지
 }
    

C++도 비슷하게 구조체를 정의하면 된다. 하지만 구조체 변수의 선언 시, 차이점이 생긴다.

C언어에서는 구조체 변수를 다음과 같이 선언할 수 있다.

struct Operator Blitz;

하지만, C++에서는 typedef나 struct 없이 다음처럼 선언하면 된다.

Operator Blitz;

 

'게임 개발 > C++언어' 카테고리의 다른 글

함수에서의 포인터 사용  (0) 2024.05.01
C++언어 포스팅 계획  (0) 2020.12.23

C++의 경우, 윤성우 저, 열혈 C++ 프로그래밍의 내용을 기반으로 포스팅 할 것이다.

또한, PART02 객체지향의 도입부터 포스팅할 것이다. (진도가 많이 나가있기에....)

(그리고 스터디 날짜에 배운 내용을 정리해서 올릴 예정이다.)

C++의 경우, 클래스, 생성자, 상속과 다형성에서 많은 공부를 해야한다고 한다. 

C가 완벽하게 잡히진 않았지만, 공부를 하면서 부족한 부분을 메꾸는 것도 나쁘지 않다고 생각한다.

'게임 개발 > C++언어' 카테고리의 다른 글

함수에서의 포인터 사용  (0) 2024.05.01
Ch03. 클래스의 기본  (0) 2020.12.23

+ Recent posts