C++的lambda表達式
Lambda 表達式簡介
Lambda 表達式(也稱為匿名函數)是一種簡潔的語法,用于定義內聯函數。它在 C++11 中引入,允許你在需要函數對象的地方直接定義函數,而無需顯式命名和聲明函數。
基本語法
[capture](parameters) -> return_type {
// function body
}
[capture]:捕獲列表,用于從外部作用域捕獲變量。可以為空或包含多個變量。(parameters):參數列表,類似于普通函數的參數。-> return_type:返回類型(可選)。如果省略,編譯器會自動推導返回類型。{ function body }:函數體,包含具體的邏輯。
捕獲列表 ([capture])
捕獲列表決定了 lambda 表達式可以訪問哪些外部變量:
[]:不捕獲任何外部變量。[=]:按值捕獲所有外部變量(復制變量的值)。[&]:按引用捕獲所有外部變量(引用外部變量)。[var]:按值捕獲指定的外部變量var。[&var]:按引用捕獲指定的外部變量var。[this]:捕獲當前類的this指針,允許訪問類成員。
示例
1. 不捕獲任何變量
auto add = [](int a, int b) {
return a + b;
};
int result = add(3, 4); // result = 7
2. 按值捕獲外部變量
int x = 10;
auto multiply = [x](int y) {
return x * y;
};
int result = multiply(5); // result = 50
3. 按引用捕獲外部變量
int x = 10;
auto increment = [&x]() {
x++;
};
increment();
std::cout << x; // 輸出 11
4. 捕獲所有外部變量(按值)
int x = 10, y = 20;
auto sum = [=]() {
return x + y;
};
int result = sum(); // result = 30
5. 捕獲所有外部變量(按引用)
int x = 10, y = 20;
auto modify = [&]() {
x *= 2;
y += 10;
};
modify();
std::cout << x << " " << y; // 輸出 20 30
6. 捕獲 this 指針
class MyClass {
public:
int value;
MyClass(int v) : value(v) {}
void print() {
auto printValue = [this]() {
std::cout << this->value << std::endl;
};
printValue();
}
};
MyClass obj(42);
obj.print(); // 輸出 42
java中的lambda表達式
Java 和 Python 中的 Lambda 表達式
雖然 C++、Java 和 Python 都支持 lambda 表達式,但它們在語法和功能上有一些差異。下面分別介紹 Java 和 Python 中的 lambda 表達式,并對比它們與 C++ 的不同之處。
1. Java 中的 Lambda 表達式
基本語法
(parameters) -> expression
或
(parameters) -> { statements; }
parameters:參數列表。expression:單行表達式(如果只有一行代碼)。{ statements; }:多行代碼塊(如果有多個語句)。
示例
1.1 不捕獲任何變量
BinaryOperator<Integer> add = (a, b) -> a + b;
int result = add.apply(3, 4); // result = 7
BinaryOperator 是 Java 標準庫中的一個函數式接口,位于 java.util.function 包中。它表示一個接受兩個輸入參數并返回一個相同類型的輸出結果的操作。BinaryOperator 是 BiFunction<T, T, T> 的特化版本,其中輸入參數和返回值的類型相同。
1.2 捕獲外部變量
Java 的 lambda 表達式不能直接修改外部局部變量,但可以訪問 final 或事實上的 final 變量(即在初始化后不再改變的變量)。
int x = 10;
BinaryOperator<Integer> multiply = (y) -> x * y;
int result = multiply.apply(5); // result = 50
1.3 使用函數式接口
Java 的 lambda 表達式通常用于實現函數式接口(只有一個抽象方法的接口),如 Comparator、Predicate、Function 等。
List<String> list = Arrays.asList("apple", "orange", "banana");
list.sort((a, b) -> a.compareTo(b));
// 或者使用方法引用
list.sort(String::compareTo);
Python 中的 Lambda 表達式
基本語法
lambda parameters: expression
parameters:參數列表。expression:單行表達式(Python 的 lambda 表達式只能包含一個表達式)。
示例
不捕獲任何變量
add = lambda a, b: a + b
result = add(3, 4) # result = 7
捕獲外部變量
Python 的 lambda 表達式可以捕獲外部變量,并且可以直接修改這些變量(只要變量是可變類型)。
x = 10
multiply = lambda y: x * y
result = multiply(5) # result = 50
在排序中使用
Python 的 sorted 函數和其他內置函數可以接受 lambda 表達式作為鍵函數。
words = ["apple", "orange", "banana"]
sorted_words = sorted(words, key=lambda word: len(word))
print(sorted_words) # 輸出 ['apple', 'banana', 'orange']
def get_length(word):
return len(word)
words = ["apple", "orange", "banana"]
sorted_words = sorted(words, key=get_length)
print(sorted_words) # 輸出: ['apple', 'banana', 'orange']
對比與總結
| 特性 | C++ | Java | Python |
|---|---|---|---|
| 語法 | [capture](params) -> type { body } |
(params) -> expression 或 { statements } |
lambda params: expression |
| 捕獲外部變量 | 支持多種捕獲方式(按值、按引用等) | 只能捕獲 final 或事實上的 final 變量 |
自動捕獲外部變量 |
| 返回類型推導 | 可以顯式指定或省略 | 推導返回類型 | 返回類型由表達式決定 |
| 函數式接口 | 無 | 必須實現函數式接口 | 無 |
| 多行代碼支持 | 支持多行代碼 | 支持多行代碼(用大括號包裹) | 只支持單行表達式 |
總結
- C++ 的 lambda 表達式功能最強大,支持多種捕獲方式和多行代碼。
- Java 的 lambda 表達式主要用于實現函數式接口,對外部變量的捕獲有嚴格限制。
- Python 的 lambda 表達式簡潔,但僅限于單行表達式,適合快速定義簡單的匿名函數。
每種語言的 lambda 表達式都有其特點和適用場景,選擇時可以根據具體需求和語言特性進行優化。
浙公網安備 33010602011771號