私はチャネルを介して関数を送信する方法と、もう一方の端で関数を実行するために余分なクローンを避ける方法を考えています。私はクロージャ内の余分なクローニング操作を削除した場合、私は次のエラーを取得する:`Fn`クロージャーでキャプチャされた外部変数から移動できません
error: cannot move out of captured outer variable in an 'Fn' closure
は、このコードは絶対に何もしませんし、グローバル可変静Sender<T>
を利用し、それは私は何を表しているという事実を無視します適切なコンパイラエラーを与えながら達成しようとしています。このコードはであり、実行されることを意図していません。、ちょうどコンパイルされています。
use std::ops::DerefMut;
use std::sync::{Arc, Mutex};
use std::collections::LinkedList;
use std::sync::mpsc::{Sender, Receiver};
type SafeList = Arc<Mutex<LinkedList<u8>>>;
type SendableFn = Arc<Mutex<(Fn() + Send + Sync + 'static)>>;
static mut tx: *mut Sender<SendableFn> = 0 as *mut Sender<SendableFn>;
fn main() {
let list: SafeList = Arc::new(Mutex::new(LinkedList::new()));
loop {
let t_list = list.clone();
run(move || {
foo(t_list.clone());
});
}
}
fn run<T: Fn() + Send + Sync + 'static>(task: T) {
unsafe {
let _ = (*tx).send(Arc::new(Mutex::new(task)));
}
}
#[allow(dead_code)]
fn execute(rx: Receiver<SendableFn>) {
for t in rx.iter() {
let mut guard = t.lock().unwrap();
let task = guard.deref_mut();
task();
}
}
#[allow(unused_variables)]
fn foo(list: SafeList) { }
このエラーを回避するにはより良い方法がありますか、チャンネルを介して機能を送信する別の方法がありますか?
残念ながら、安定性は私の唯一の選択肢です。あなたがすでに試してみたことを確認したように見えますが、他の誰かが夜間に使う能力を持つこのスーパーの人を助けてくれるかもしれません。ありがとう:) – nathansizemore
ハックを使用することができます。 'Fn'を使い、' take 'で移動する 'Option'sで動くだけです。 'Fn'を誤って使用したときにランタイムエラーが発生する –
ライブラリ要件のために' Fn'が必要な場合はどうすればいいですか? –