C++11 นำเสนอ Lambda Expressions แต่ C++14 ปรับปรุงให้รองรับ Generalized (Generic) Lambdas ที่สามารถรับพารามิเตอร์แบบ auto ได้ ทำให้ Lambda เดียวสามารถทำงานกับหลายชนิดข้อมูล (Polymorphic)
Syntax
[](auto x, auto y) { return x + y; }
คีย์เวิร์ด auto ในพารามิเตอร์ทำให้ Compiler สร้าง Template แบบ Implicit ให้อัตโนมัติ
ตัวอย่างโค้ด
#include <iostream>
#include <string>
using namespace std;
int main() {
// Generalized Lambda: รับ auto parameters
auto add = [](auto arg1, auto arg2) {
return arg1 + arg2;
};
// ทำงานกับ int
cout << "Sum of integers: " << add(5, 8) << endl;
// ทำงานกับ float/double
cout << "Sum of floats: " << add(2.75, 5.639) << endl;
// ทำงานกับ string (Concatenation)
cout << "Concatenate Strings: "
<< add(string("Hello "), string("World")) << endl;
return 0;
}
ผลลัพธ์
Sum of integers: 13 Sum of floats: 8.389 Concatenate Strings: Hello World
วิธีทำงานภายใน (Conceptual)
Compiler จะแปลง Generalized Lambda เป็น Functor Class ที่มี operator() แบบ Template:
struct __lambda_1 {
template <typename T, typename U>
auto operator()(T arg1, U arg2) const {
return arg1 + arg2;
}
};
ข้อดีของ Generalized Lambda
- Code Reuse: Lambda เดียวใช้ได้หลาย Type
- Type Safety: ตรวจสอบ Type ที่ Compile Time
- Performance: ไม่มี Overhead จาก Type Erasure (เหมือน std::function)
- Clean Syntax: เขียนสั้นกว่า Template Function ธรรมดา
การใช้งานขั้นสูง
// Generic Lambda กับ Container
auto print = [](const auto& container) {
for (const auto& item : container) {
cout << item << ' ';
}
cout << '\n';
};
vector<int> v = {1,2,3};
list<string> l = {"a","b","c"};
print(v); // 1 2 3
print(l); // a b c
// Generic Lambda ใน STL Algorithms
auto is_even = [](auto x) { return x % 2 == 0; };
vector<int> nums = {1,2,3,4,5,6};
auto it = find_if(nums.begin(), nums.end(), is_even);
ข้อจำกัด
- ต้องใช้ C++14 ขึ้นไป (
-std=c++14) - ไม่สามารถระบุ Return Type แบบ Explicit ได้ (ต้องใช้
autoreturn) - ไม่รองรับ Variadic Parameters (
auto... args) จนถึง C++20