함수의 정의와 호출
함수의 기본 구조
C++에서 함수의 기본 구조는 다음과 같습니다.
반환타입 함수이름(매개변수 목록) {
// 함수 본문
return 반환값;
}
- 반환타입 : 함수가 작업을 마치고 반환하는 값의 데이터 타입
- 함수이름 : 함수를 식별하는 이름
- 매개변수 목록 : 함수에 전달되는 값들의 목록
- 함수 본문 : 함수가 수행하는 실제 작업
- return 문 : 함수의 결과를 호출자에게 반환
함수 정의 예시
#include <iostream>
int add(int a, int b) {
return a + b;
}
int main() {
int result = add(5, 3);
std::cout << "5 + 3 = " << result << std::endl;
return 0;
}
이 예제에서 add
함수는 두 정수를 받아 그 합을 반환합니다.
함수 호출
함수를 호출할 때는 함수 이름과 필요한 인자를 제공합니다.
int result = add(5, 3); // result는 8
매개변수 전달 방식
C++에서는 세 가지 주요 매개변수 전달 방식이 있습니다.
값에 의한 전달 (Pass by Value)
void incrementByValue(int x) {
x++; // 원본 변수에 영향을 주지 않음
}
int main() {
int num = 5;
incrementByValue(num);
std::cout << num << std::endl; // 출력: 5
return 0;
}
참조에 의한 전달 (Pass by Reference)
void incrementByReference(int& x) {
x++; // 원본 변수를 직접 수정
}
int main() {
int num = 5;
incrementByReference(num);
std::cout << num << std::endl; // 출력: 6
return 0;
}
포인터에 의한 전달 (Pass by Pointer)
void incrementByPointer(int* x) {
(*x)++; // 포인터를 통해 원본 변수를 수정
}
int main() {
int num = 5;
incrementByPointer(&num);
std::cout << num << std::endl; // 출력: 6
return 0;
}
반환 값
함수는 다양한 방식으로 값을 반환할 수 있습니다.
단일 값 반환
int square(int x) {
return x * x;
}
참조 반환
int& getElement(std::vector<int>& vec, int index) {
return vec[index];
}
void (반환 값 없음)
void printMessage(const std::string& msg) {
std::cout << msg << std::endl;
}
함수 프로토타입
함수 프로토타입을 사용하면 함수의 선언과 정의를 분리할 수 있습니다.
// 함수 프로토타입
int multiply(int a, int b);
int main() {
std::cout << multiply(4, 5) << std::endl; // 출력: 20
return 0;
}
// 함수 정의
int multiply(int a, int b) {
return a * b;
}
기본 매개변수
함수의 매개변수에 기본값을 지정할 수 있습니다.
void greet(const std::string& name = "Guest") {
std::cout << "Hello, " << name << "!" << std::endl;
}
int main() {
greet(); // 출력: Hello, Guest!
greet("Alice"); // 출력: Hello, Alice!
return 0;
}
함수 오버로딩
C++에서는 같은 이름의 함수를 매개변수의 타입이나 개수를 달리하여 여러 개 정의할 수 있습니다.
int add(int a, int b) { return a + b; }
double add(double a, double b) { return a + b; }
int main() {
std::cout << add(5, 3) << std::endl; // int 버전 호출
std::cout << add(3.14, 2.5) << std::endl; // double 버전 호출
return 0;
}
인라인 함수
작은 함수를 최적화하기 위해 인라인 함수를 사용할 수 있습니다.
inline int square(int x) { return x * x; }
int main() {
std::cout << square(5) << std::endl; // 컴파일러가 최적화할 수 있음
return 0;
}
재귀 함수
함수가 자기 자신을 호출하는 방식을 재귀라고 합니다.
int factorial(int n) {
if (n <= 1) return 1;
return n * factorial(n - 1);
}
int main() {
std::cout << factorial(5) << std::endl; // 출력: 120
return 0;
}
연습 문제
- 두 수를 입력받아 최대공약수(GCD)를 계산하는 함수를 작성하세요.
- 재귀 함수를 사용하여 피보나치 수열의 n번째 항을 계산하는 함수를 구현하세요.
- 함수 오버로딩을 사용하여 정수, 실수, 문자열을 인자로 받아 각각의 타입에 맞는 출력을 하는 print 함수를 작성하세요.
- 참조에 의한 전달을 사용하여 두 변수의 값을 교환하는 swap 함수를 구현하세요.
참고자료
- C++ 공식 문서의 함수 섹션 : C++ Functions
- "Effective C++" by Scott Meyers (항목 23 : 멤버 함수보다는 비멤버 비프렌드 함수를 선호하라)
- "C++ Primer" by Stanley B. Lippman, Josée Lajoie, and Barbara E. Moo (Chapter 6: Functions)
- C++ Core Guidelines의 함수 관련 규칙 : F : Functions