지난시간에 배운 call by value, call by address, call by reference를 통해 구조체가 매개변수로 어떻게 전달되는지 알아보자.
call by value를 통한 구조체 매개변수 전달
#include <iostream>
using namespace std;
struct Rectangle {
int length;
int breadth;
};
int area(struct Rectangle r1)
{
r1.length = 2;
return r1.breadth * r1.length;
}
int main()
{
struct Rectangle r = { 10,5};
cout << area(r) << endl;
return 0;
}
- length = 10, breath = 5로 구조체가 초기화됬고, area(r)을 호출하는데 r1 매개변수로 구조체 그대로 area 스택에 그대로 복사한다.
- 여기서 중요한 점은 call by value는 parameter가 변해도, argument에 영향을 미치지 않지만, 함수가 종료될 때의 반환값은 그대로 복사된다. 즉, area(r) = 50이 아니라 변경된 값인 10이 나온다.(사칙연산은 call by value로 값을 그대로 main에 전달할 수 있음!)
💡구조체를 먼저 선언해야 컴파일러는 그 다음의 함수들을 처리할 수 있다.
call by address를 통한 구조체 매개변수 전달
#include <iostream>
using namespace std;
struct Rectangle {
int length;
int breadth;
};
void changelength(Rectangle* p, int n)
{
p->length = n;
}
int main()
{
Rectangle r = { 10,5 };
changelength(&r, 20);
cout << r.length << endl;
return 0;
}
- 포인터가 주소를 가리킨다는 call by address를 이용하여 main함수 내의 초기화된 멤버변수의 값을 변경할 수 있다.
- 즉, 구조체의 포인터를 p로 선언하여, 멤버변수에 간접참조하여 changelength 스택에서 20이 복사된 n으로 변경한 값이 반영된다는 것이다.
call by reference를 통한 구조체 매개변수 전달
#include <iostream>
using namespace std;
struct Rectangle {
int length;
int breadth;
};
void changelength(Rectangle& p, int n)
{
p.length = n;
}
int main()
{
Rectangle r = { 10,5 };
changelength(r, 20);
cout << r.length << endl;
return 0;
}
- 위의 call by address의 진화버전이다. argument에서 &를 지우고, parameter의 포인터를 참조자로 바꾸면 끝
- 참조자 p는 r의 별명이기 때문에 둘은 같은 스택프레임 내에서 멤버변수들을 공유한다.