A closure can be cloneable when all variables captured are cloneable:
let foo=Box::new(||{});
let bar=(*foo).clone();
Above code can be compile.
But following code:
let foo:Box<FnMut()>=Box::new(||{});
let bar=(*foo).clone();
cannot.
If I want to return a closure from a function, I have to return Box<FnMut()>, which however is not cloneable.
My question is that is there a way to make Box<FnMut()> cloneable?
jonh
2
Can't call clone on unsized types, could try something like either;
trait MyFn {
fn call(&mut self);
fn box_clone(self: Box<Self>) -> Box<MyFn>;
}
impl<F: 'static + Clone + FnMut()> MyFn for F {
fn call(&mut self) {
self()
}
fn box_clone(self: Box<Self>) -> Box<MyFn> {
self.clone()
}
}
trait MyFnImpl: Clone + FnMut() {}
impl<F: 'static + Clone + FnMut()> MyFnImpl for F {}
fn it() -> impl MyFnImpl {
|| {}
}
fn main() {
let foo = Box::new(||{}) as Box<MyFn>;
let mut bar = foo.box_clone();
bar.call();
let it = it();
let mut it2 = it.clone();
it2();
}
1 Like
impl Trait in return position is about to become stable so just wait for that to return closures:
fn get() -> impl FnMut() + Clone {
|| ()
}
// If you really want a box
fn get_boxed() -> Box<impl FnMut() + Clone> {
Box::new(||())
}
Note that neither of these cases use a trait object.
1 Like