코딩을 하다보면 한번만 만드는 함수를 만드는경우가 있다.
물론 나중에 다른곳에서 쓰면 다행이지만 그런게아니라면 실행중인 함수에서 끝내는것이 좋다.
// 숫자가 10보다 큰지 확인하는 함수
bool isGreaterThanTen(int n) {
return n > 10;
}
int main() {
std::vector<int> numbers = {5, 12, 3, 15, 8};
// numbers에서 10보다 큰 첫 번째 원소를 찾고 싶다.
auto it = std::find_if(numbers.begin(), numbers.end(), isGreaterThanTen);
}
예시로 하나 가져왔다 isGreaterThanTen함수를 한번만 쓴다고 볼때
따로 빼는거 자체가 코드를 이동해야해서 이해가 어렵다
// 람다식으로 표현
auto it = std::find_if(numbers.begin(), numbers.end(), [](int n) {
return n > 10;
});
이렇게하면 프로그래머는 it부분을 보고 isGreaterThanTen 함수를 찾아가서 뭐하는 함수인지 확인을하고 다시 돌아올 필요가 없는것이다.
근데 여기서 드는 생각이 하나 있을껀데 그냥 이함수에서 코딩 짜는게 좋은거 아닌가 하는 생각이 든다.
// 람다를 사용한 경우
auto it = std::find_if(numbers.begin(), numbers.end(), [](int n) {
return n > 10;
});
// 그냥 for문으로 직접 코딩한 경우
auto it_for = numbers.end();
for (auto it = numbers.begin(); it != numbers.end(); ++it) {
if (*it > 10) {
it_for = it;
break;
}
}
이렇게 보면 그냥 쓰는거랑 다른데 없어보이는데 이제 부터 람다식의 기능을 설명하겠습니다.
auto it = std::find_if(numbers.begin(), numbers.end(), [](int n) {
return n > 10;
});
// 부분에서 일부만 가지고왔다.
[](int n) {
return n > 10;
}
1. [] : 외부의 변수를 받아오는 구문이다.
int offset = 10;
std::for_each(v.begin(), v.end(), [offset](int& n) {
n += offset; // 외부 변수 offset을 값을 가지고 왔다.
});
// offset 변수를 함수안에서 잠시 사용 하는 모습 이때 캡쳐해서 사용한다.
2. () (매개변수): 일반 함수처럼 매개변수를 받는 부분입니다.
3. { } 로직 : 로직이 돌아가는 부분이다.
이 구조를 이용해서 활용을 해본다면
std::vector<int> v = {3, 1, 4, 1, 5, 9};
// 1. 정렬 하기
std::sort(v.begin(), v.end(), [](int a, int b) {
return a > b; // 내림차순으로 정렬
});
int offset = 10;
std::for_each(v.begin(), v.end(), [offset](int& n) {
n += offset; // 외부 변수 offset을 값을 가지고 왔다.
});
같은 함수 내에서 여러번 사용하더라도 변수에 저장하고 사용할수도있다.
// 덧셈을 수행하는 람다를 변수에 저장
auto adder = [](int a, int b) {
return a + b;
};
int result1 = adder(10, 20);
int result2 = adder(5, 7);
std::function 을 이용할수도 있다
#include <functional>
std::function<int(int, int)> operation;
// 덧셈 람다를 할당
operation = [](int a, int b) { return a + b; };
std::cout << operation(10, 20) << std::endl; // 30
// 뺄셈 람다를 할당
operation = [](int a, int b) { return a - b; };
std::cout << operation(10, 20) << std::endl; // -10
최근에 cpp에는 기존과 달리 매개변수를 auto로 지정 가능 하다.
auto generic_adder = [](auto a, auto b) {
return a + b;
};
int sum_int = generic_adder(5, 10);
double sum_double = generic_adder(3.14, 2.71);
std::string s = generic_adder(std::string("hello "), std::string("world"));
int double std::string등등 가능합니다.