Rust Specs 0.20泛型组件可变Join方法报错求助
问题分析与解决
这个错误不是Specs 0.20的bug,而是版本升级后对可变Join操作的trait约束收紧导致的——0.19版本的约束更宽松,而0.20重构了存储层的相关逻辑,要求显式满足额外的trait条件才能进行可变Join。
错误根源
你当前的泛型约束只要求T: Component,但可变Join(&mut WriteStorage参与的Join)需要满足两个额外条件:
T对应的存储类型必须实现SharedGetMutStorage<T>trait(这是可变访问存储的核心约束)&mut WriteStorage<'a, T>必须实现Jointrait(由前者间接推导,但需要显式声明约束)
修复方案
修改System实现的where子句,补充以下两个约束:
<T as specs::Component>::Storage: specs::storage::SharedGetMutStorage<T>, &mut specs::WriteStorage<'a, T>: specs::Join,
完整的impl System代码如下:
impl<'a, T> System<'a> for ChangeVariableSystem<T> where T: Component + Variable + Default + Send + Sync + 'static, <T as specs::Component>::Storage: specs::storage::SharedGetMutStorage<T>, &mut specs::WriteStorage<'a, T>: specs::Join, { type SystemData = ( ReadStorage<'a, FooMarker>, WriteStorage<'a, T>, ); fn run(&mut self, data: Self::SystemData) { let ( markers, mut variables, ) = data; (&variables, &markers).join() .for_each(|(variable, _)| { variable.get_value(); println!("{:?}", variable); }); (&mut variables, &markers).join() .for_each(|(variable, _)| { variable.set_value(1.0); println!("{:?}", variable); }); } }
补充说明
- 对于常用的存储类型(比如
VecStorage、HashMapStorage),它们默认已经实现了SharedGetMutStorage,所以这个约束不会影响具体组件(比如你的Foo)的使用 - 不可变Join(
&ReadStorage或&WriteStorage)不需要这些约束,因为其对应的trait要求更宽松,这也是第一个Join能正常工作的原因
内容的提问来源于stack exchange,提问作者Sergio Cavaleiro Costa
相关产品推荐
相关产品推荐

