闭包会根据捕获变量的类型来自动实现 Clone
、Copy
、Send
和 Sync
,当定义一个闭包时 || {...}
,他可以是 Fn
、FnMut
或 FnOnce
(这些也是特征),当然还可以把他限定成 Fn + Clone
、Fn + Copy
等,比如:
fn new<F>(function: F)
where
F: Fn() + Clone,
{
let f = function.clone();
f();
}
new(||{});
这里限定了 F
必须是一个 Fn()
闭包(特征),并且实现了 Clone
特征,所以对 function
进行 clone
是没问题的。
这里实参传入 ||{}
不会报错,由于闭包中没有捕获变量,所以闭包能够自动实现 Clone
特征,符合 trait bound。
但如果 F
捕获了一个没有实现 Clone
的变量,这里就会报错,比如:
struct Bar;
fn new<F>(function: F)
where
F: Fn() + Clone,
{
let f = function.clone();
f();
}
let bar = Bar;
new(||{
bar;
})
因为 Bar
没有实现 Clone
,bar
被捕获,所以导致闭包也无法自动实现 Clone
,不符合 trait bound。