首页 > 解决方案 > 弱引用其所有者的结构的构造函数

问题描述

试图实现一个数据结构,其中许多“事物”可以由一个“所有者”拥有,而每个“事物”都应该知道它的所有者是谁。据我了解,可以通过在每个“事物”中对所有者进行弱引用来实现。我无法弄清楚如何new为这些结构实现构造函数 () 的问题。这是我正在尝试做的简化结构:

use std::rc::{Rc, Weak};

struct Owner {
    thing1: Thing,
    thing2: Thing,
}

impl Owner {
    fn new() -> Self {
        Self {
            thing1: Thing::new(???),   // 1
            thing2: Thing::new(???),   // 1
        }
    }
}

struct Thing {
    owner: Weak<Owner>,
    value: u32,
}

impl Thing {
    fn new(owner: ???) -> Self {      // 2
        Self {
            owner: Weak::clone(???),  // 2
            value: 0,
        }
    }
}

所以在这里我无法弄清楚两件事:

  1. 构造所有者时-如何将自己作为参数传递给“事物”的构造函数?
  2. 构建事物时 - 如何准确地创建对所有者的引用?

也许我的方法是完全错误的,在这种情况下,请提出正确的方法。

更新:
这种结构用例的更具体示例:考虑电子电路模拟,其中每个“事物”都是电子元件的引脚,即“所有者”。因此,每次外部更改引脚的值时,都应该触发所有者组件,这反过来又会更改其他连接器的值。

标签: rust

解决方案


首先,正如其他人所提到的,这可能是一个坏主意,不仅会导致性能不佳,而且很难编写代码。有了这个警告,就可以回答了。

这有点棘手,因为今天在稳定的 Rust 中,您需要初始化所有者才能获得对它的引用(因此您可能需要每个字段都是Option<Thing>; 不理想)。

但是,幸运的是,有一种新的不稳定方法Rc::new_cyclic,我认为它完全符合您的要求:

操场

#![feature(arc_new_cyclic)]

use std::rc::{Rc, Weak};

struct Owner {
    thing1: Thing,
    thing2: Thing,
}

impl Owner {
    fn new() -> Rc<Self> {
        Rc::new_cyclic(|weak| {
            Self {
                thing1: Thing::new(weak.clone()),
                thing2: Thing::new(weak.clone()),
            }
        })
    }
}

struct Thing {
    owner: Weak<Owner>,
    value: u32,
}

impl Thing {
    fn new(owner: Weak<Owner>) -> Self {
        Self {
            owner,
            value: 0,
        }
    }
}

推荐阅读