تمرير الإغلاق مرتين دون أن يبتعد
سؤال
أقوم بتجربة عمليات الإغلاق:
fn call_it(f: ||) {
f();
}
let klosure = || println("closure!");
call_it(klosure);
call_it(klosure); //Blows up here
يؤدي تمرير klosure إلى call_it() مرتين إلى حدوث خطأ في المترجم بسبب نقل قيمة الإغلاق:
closures.rs:16:13: 16:20 error: use of moved value: `klosure`
closures.rs:16 call_it(klosure);
^~~~~~~
closures.rs:15:13: 15:20 note: `closure` moved here because it has type `||`, which is a non-copyable stack closure (capture it in a new closure, e.g. `|x| f(x)`, to override)
closures.rs:15 call_it(klosure);
^~~~~~~
يقدم المترجم بالفعل اقتراحًا حول كيفية حل المشكلة، لكنني لم أكتشف طريقة لتطبيقه بنجاح.
أي اقتراحات؟:د
المحلول
ملحوظة:تم نقل `الإغلاق` هنا لأنه يحتوي على النوع `||`، وهو إغلاق مكدس غير قابل للنسخ (التقطه في إغلاق جديد، على سبيل المثال.`| x | f (x) `، لتجاوز)
هذا يعني أنك ستكتب || closure()
بدلاً من closure
:أنت تمر بإغلاق جديد يستدعي إغلاقك الأول.
نصائح أخرى
(تحديث:لا تفعل هذا، فقد يتم رفضه في المستقبل القريب.أ &mut ||
من المحتمل أن تعمل بشكل جيد الآن وفي المستقبل.انظر المناقشة والروابط في التعليقات على هذه الإجابة.)
نهج محتمل آخر (على الرغم من أنه أقبح قليلاً للقراءة):
fn call_it(f_ref: &||) { // now takes a borrowed reference to a closure
(*f_ref)();
}
let klosure = || println("closure!");
call_it(&klosure);
call_it(&klosure);
لا تنتمي إلى StackOverflow