我现在使用rust-sfml
(rsfml::graphics
)向屏幕绘制像素。 (我只是从Rust和项目开始。)我将数据存储在Image
中,然后复制到Texture
。
此Texture
用于创建Sprite<'s>
;这是我的问题。我需要能够改变Texture
,但Sprite<'s>
的类型似乎可以保证我不能做我想做的事情。由于每次重绘窗口时我都需要能够调用window.draw(&sprite)
,因此我每次只创建一个新的Sprite
。
优选的替代方案是将Sprite<'s>
与struct Render
一起保留在Texture
中。因为&#39; Sprite&#39;有一个生命周期参数,它变为struct Render<'s>
:
struct Render<'s> {
texture: Texture,
sprite: Sprite<'s>,
}
我在Render
上有一个方法:
fn blit(&'s mut self) -> ()
改变Render
(通过编辑Texture
)。现在,只要我尝试多次调用blit
,我就遇到了这个问题:
render.blit();
render.blit(); // error: cannot borrow `render` as mutable more than once at a time
我认为,这是因为生命周期参数强制Render
的生命周期借用 - blit
- 调用等于Render
实例的生命周期(整个主要功能)。
如何保留原始Sprite
并继续改变容器?有可能吗?
这是一个看起来很愚蠢且相当简单的例子:
extern crate rsfml;
use rsfml::graphics::Sprite;
fn main() -> () {
let mut render = Render::new();
render.blit();
render.blit(); // error: cannot borrow `render` as mutable more than once at a time
}
struct Render<'s> {
sprite: Option<Sprite<'s>>,
}
impl<'s> Render<'s> {
fn new() -> Render { Render { sprite: None } }
fn blit(&'s mut self) -> () { }
}
(如果问题不明确,请道歉。当我对这些概念不太熟悉时,很难表达。)
答案 0 :(得分:2)
当你致电blit
时,有两个生命周期在考虑之中;你知道,self
类型&'ρ₀ Render<'ρ₁>
的某些寿命ρ0和ρ1。在你的impl<'s> Render<'s>
声明中,你已经声明ρ1是's
,并且在你的&'s mut self
中你宣称ρ是's
:因此,借用{的生命周期{ {1}} 是self
,这意味着您只能拥有一个借用,因为它将一直存在,直到类型的破坏 - 它被声明为“至少与被称为“。
您希望对此进行更改,以便为's
函数引入 new 生命周期参数,该参数允许小于blit
;你希望ρ0是最小的,只与返回值绑定(因为我认为你实际上正在使用's
- 如果没有,你应该省略它并允许编译器推断我们将要显式写入的内容) 。这样,借用只会在函数的返回值仍然在范围内时才会激活(在你的例子中,它没有被使用,所以你可以立即采取另一个参考)。
然后,这是对需要完成的功能的改变:
's
如果您将此更改为具有返回值并使用它,则在再次调用fn blit<'a>(&'a mut self) { }
之前,您需要确保它超出范围。这可能意味着将其直接传递给一个函数,或者它可能意味着引入一个新的范围,如下所示:
blit