如何声明和实现一个跟踪结构集合的结构?
How to declare and implement a struct that keeps track of a collection of structs?
我有一个结构,称之为 Master
,它需要一个字段 slaves
,它是 Slave
的集合。添加到 Master
时,每个 Slave
都需要使用 Master
分配给它的唯一 ID 进行标记。
我目前尝试这样做的方式是这样的:
pub struct Master {
slaves: VecMap<Slave>
}
impl Master {
// omitted constructor
// fn get_unique_id(&self) -> usize {...}
pub fn add_slave(&mut self, slave: &mut Slave) {
let new_id = self.get_unique_id();
slave.set_id(new_id);
self.slaves.insert(new_id, *slave);
// Previous line causes "cannot move out of borrowed content" error
}
pub fn get_slave(&self, id: usize) -> Option<&Slave> {
self.slaves.get(&id)
}
}
我应该如何声明从属字段(VecMap
of refs or values)并正确实现这些方法?
容器包含值。在这种情况下,您正在获取 reference (slave: &mut Slave
),然后试图 窃取 Slave
的所有权在你的函数中。这是一个很大的禁忌,因为此方法的调用者不会知道您已经消费了该项目。
相反,在添加项目时放弃其所有权:
pub fn add_slave(&mut self, slave: Slave) {
let mut slave = slave; // let us mutate it, now that we own it
let new_id = self.get_unique_id();
slave.set_id(new_id);
self.slaves.insert(new_id, slave);
}
我更喜欢接受项目 (slave: Slave
),然后在函数体中使其可变。这样,方法的调用者就不需要关心实现细节。如果这让您感到困扰,您也可以将参数声明为 mut slave: Slave
。
另一种选择是更改您的结构以保存 &mut Slave
个项目,但我猜您想要第一个解决方案。
我有一个结构,称之为 Master
,它需要一个字段 slaves
,它是 Slave
的集合。添加到 Master
时,每个 Slave
都需要使用 Master
分配给它的唯一 ID 进行标记。
我目前尝试这样做的方式是这样的:
pub struct Master {
slaves: VecMap<Slave>
}
impl Master {
// omitted constructor
// fn get_unique_id(&self) -> usize {...}
pub fn add_slave(&mut self, slave: &mut Slave) {
let new_id = self.get_unique_id();
slave.set_id(new_id);
self.slaves.insert(new_id, *slave);
// Previous line causes "cannot move out of borrowed content" error
}
pub fn get_slave(&self, id: usize) -> Option<&Slave> {
self.slaves.get(&id)
}
}
我应该如何声明从属字段(VecMap
of refs or values)并正确实现这些方法?
容器包含值。在这种情况下,您正在获取 reference (slave: &mut Slave
),然后试图 窃取 Slave
的所有权在你的函数中。这是一个很大的禁忌,因为此方法的调用者不会知道您已经消费了该项目。
相反,在添加项目时放弃其所有权:
pub fn add_slave(&mut self, slave: Slave) {
let mut slave = slave; // let us mutate it, now that we own it
let new_id = self.get_unique_id();
slave.set_id(new_id);
self.slaves.insert(new_id, slave);
}
我更喜欢接受项目 (slave: Slave
),然后在函数体中使其可变。这样,方法的调用者就不需要关心实现细节。如果这让您感到困扰,您也可以将参数声明为 mut slave: Slave
。
另一种选择是更改您的结构以保存 &mut Slave
个项目,但我猜您想要第一个解决方案。