Was ist der richtige Smart Pointer, um mehrere starke Referenzen zu haben und Veränderlichkeit zuzulassen?

Ich möchte eine Struktur mit zwei Referenzen auf dem Heap haben. eine für mich und eine aus einer schließung. Beachten Sie, dass der Code für den Singlethread-Fall gilt:

use std::rc::Rc;

#[derive(Debug)]
struct Foo {
    val: u32,
}
impl Foo {
    fn set_val(&mut self, val: u32) {
        self.val = val;
    }
}
impl Drop for Foo {
    fn drop(&mut self) {
        println!("we drop {:?}", self);
    }
}

fn need_callback(mut cb: Box<FnMut(u32)>) {
    cb(17);
}

fn create() -> Rc<Foo> {
    let rc = Rc::new(Foo { val: 5 });
    let weak_rc = Rc::downgrade(&rc);
    need_callback(Box::new(move |x| {
        if let Some(mut rc) = weak_rc.upgrade() {
            if let Some(foo) = Rc::get_mut(&mut rc) {
                foo.set_val(x);
            }
        }
    }));
    rc
}

fn main() {
    create();
}

Im realen Code,need_callback speichert den Rückruf an einem Ort, kann aber vorher @ aufrufcb wieneed_callback does.

Der Code zeigt, dassstd::rc::Rc ist für diese Aufgabe nicht geeignet, dafoo.set_val(x) wird nie aufgerufen; Ich habe zwei starke Referenzen undRc::get_mut gibtNone in diesem Fall

Welchen intelligenten Zeiger mit Referenzzählung soll ich anstelle von @ verwendestd::rc::Rc um es möglich zu machen @ anzuruffoo.set_val? Vielleicht ist es möglich, meinen Code zu reparieren und trotzdem @ zu verwendstd::rc::Rc?

Nach einigem Nachdenken brauche ich so etwas wiestd::rc::Rc, aber schwache Referenzen sollten ein Fallenlassen verhindern. Ich kann zwei schwache Referenzen haben und sie zu starken aufrüsten, wenn ich Veränderbarkeit benötige.

Da es sich um ein Singlethread-Programm handelt, habe ich immer nur starke Referenzen, sodass alles wie erwartet funktioniert.

Antworten auf die Frage(2)

Ihre Antwort auf die Frage