* 개인적인 공부 내용을 기록하는 용도로 작성한 글 이기에 잘못된 내용을 포함하고 있을 수 있습니다.
#1 값에 의한 전달 Call-By-Value
#2 참조에 의한 전달 Call-By-Reference
#1 값에 의한 전달 Call-By-Value
Call-By-Value 방식은 인자로 넘기는 값을 "복사"하여 함수에 넘겨주는 방식입니다. 즉, 값의 복사에 의한 함수 호출을 의미합니다.
다음 코드는 main() 함수에서 doSomething 함수로 x의 값 5를 전달해 출력하는 예제입니다.
유의해야 할 점은 x가 직접 전달되는 것이 아닌 x의 값 "5"만이 전달되는 것으로 doSomething 함수의 파라미터 x와 main() 함수의 x는 서로 다른 메모리에 할당되어 있습니다. 따라서, 각 함수에서 x의 주소값을 출력해보면 전혀 다른 주소가 출력됩니다.
// int x 메모리 선언.
// int x 메모리에 값이 복사가 되어 초기화
// Call-By-Value
void doSomething(int x) {
cout << "doSomething() " << x << " " << &x << endl;
}
int main(){
// call-by-value
int x = 5;
doSomething(x); // x가 직접 전달되는 것이 아니라, x의 값 "5"만이 전달된다
cout << "main() " << x << " " << &x << endl;
return 0;
}
doSomething() 5 0x7ffc942b605c
main() 5 0x7ffc942b6074
값에 의한 전달은 값을 복사해서 전달하기에, "원본의 값에 영향을 미칠 수 없으며", 값을 넘겨줄 때 마다 새로운 메모리를 복사해 할당해야 하기에 복사손실 문제를 지니고 있습니다.
아래 코드와 같이 doSomething 함수에서 x의 값을 6으로 변경해도 main 함수부에는 전혀 영향을 끼치지 못함을 확인할 수 있습니다.
// int x 메모리 선언.
// int x 메모리에 값이 복사가 되어 초기화
// Call-By-Value
void doSomething(int x) {
x = 6;
cout << "doSomething() " << x << " " << &x << endl;
}
int main(){
// call-by-value
int x= 5;
doSomething(x);
cout << "main() " << x << " " << &x << endl;
return 0;
}
doSomething() 6 0x7ffe7651420c
main() 5 0x7ffe76514224
#2 참조에 의한 전달 Call-By-Reference
Call-By-Reference 방식은 함수의 인자에 변수 자체를 즉, 주소값을 넘겨주는 방식입니다. 변수의 주소를 넘겨주기에, Call-By-Value 방식과 달리 원본의 값에 직접 영향을 미칩니다.
다음 코드는 main() 함수부에서 addOne() 함수로 직접 y의 주소를 넘겨 y의 값을 1 더해주는 예제입니다.
출력 결과를 확인해보면 main() 함수의 y의 값도 6으로 증가해 있음을 확인할 수 있습니다. 또한 addOne에서의 y와 main()에서의 y의 주소가 동일합니다.
// Call-By-Reference
void addOne(int &y) {
y = y + 1;
cout << "addOne() " << y << " " << &y << endl;
}
int main(){
// call-by-ref
int y = 5;
addOne(y);
cout << "main() " << y << " " << &y << endl;
return 0;
}
addOne() 6 0x7ffd933425d4
main() 6 0x7ffd933425d4
Call-By-Value 와 Call-By-Reference 방식의 특징에 대해 정리하고 마치도록 하겠습니다.
Call-By-Value 방식은 원본의 데이터에 영향을 끼칠 수 없고, 값을 넘겨줄 때 마다 매번 새로운 메모리를 할당해야 하기에, 복사손실 문제를 갖고 있다는 단점을 가지고 있습니다.
Call-By-Reference 방식은 원본의 데이터에 영향을 끼칠 수 있으며, 직접 주소를 넘겨주는 방식이기에 새로운 메모리를 할당할 필요가 없어 복사손실 문제에서 자유롭다는 장점을 가지고 있습니다.
'Archive2 > C&C++' 카테고리의 다른 글
[C/C++] 함수의 리턴값으로 주소(포인터) 참조자를 받을 시 유의점 (0) | 2022.02.08 |
---|---|
[C/C++] const int& vs const int (0) | 2022.02.06 |
[C++] 문자열 기호적 상수 (char[] vs char* vs const char*) (0) | 2022.02.02 |
[C/C++] 포인터와 const (feat. const 키워드의 위치에 따른 차이점) (0) | 2022.02.02 |
[C/C++] 포인터란? _ * & nullptr (0) | 2022.01.27 |