Created
April 29, 2018 18:39
-
-
Save vadixidav/3836ca64b2eb389797d0fb94f1733f37 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
error[E0499]: cannot borrow `*self` as mutable more than once at a time | |
--> src\grid.rs:199:9 | |
| | |
198 | self.step(); | |
| ---- first mutable borrow occurs here | |
199 | self.update(); | |
| ^^^^ second mutable borrow occurs here | |
200 | } | |
| - first borrow ends here | |
error[E0506]: cannot assign to `self.diffs` because it is borrowed | |
--> src\grid.rs:203:9 | |
| | |
203 | self.diffs = self.make_diffs(); | |
| ^^^^^^^^^^^^^----^^^^^^^^^^^^^ | |
| | | | |
| | borrow of `self.diffs` occurs here | |
| assignment to borrowed `self.diffs` occurs here | |
error: aborting due to 2 previous errors | |
/// Represents the state of the simulation. | |
#[derive(Clone, Debug)] | |
pub struct SquareGrid<S: Sim> { | |
cells: Vec<S::Cell>, | |
diffs: Vec<ManuallyDrop<(S::Diff, S::MoveNeighbors)>>, | |
width: usize, | |
height: usize, | |
} | |
... | |
impl<'a, S, C, D, M, N, MN> SquareGrid<S> | |
where | |
S: Sim<Cell = C, Diff = D, Move = M, Neighbors = N, MoveNeighbors = MN>, | |
S::Cell: Sync + Send, | |
S::Diff: Sync + Send, | |
S::Move: Sync + Send, | |
S::Neighbors: Sync + Send, | |
S::MoveNeighbors: Sync + Send, | |
Self: GetNeighbors<'a, usize, N>, | |
Self: TakeMoveNeighbors<usize, MN>, | |
{ | |
/// Run the Grid for one cycle and parallelize the simulation. | |
pub fn cycle(&'a mut self) { | |
self.step(); | |
self.update(); | |
} | |
fn step(&'a mut self) { | |
self.diffs = self.make_diffs(); | |
} | |
fn make_diffs(&'a self) -> Vec<ManuallyDrop<(S::Diff, S::MoveNeighbors)>> { | |
self.cells[..] | |
.par_iter() | |
.enumerate() | |
.map(|(ix, c)| S::step(c, self.get_neighbors(ix))) | |
.map(ManuallyDrop::new) | |
.collect() | |
} | |
fn update(&'a mut self) { | |
self.cells[..] | |
.par_iter() | |
.enumerate() | |
.for_each(|(ix, cell)| unsafe { | |
S::update( | |
transmute(cell), | |
self.take_diff(ix), | |
(self as &Self).take_move_neighbors(ix), | |
); | |
}); | |
// This wont call any `drop()` because of the `ManuallyDrop`. | |
self.diffs.clear(); | |
} | |
} |
Author
vadixidav
commented
Apr 29, 2018
error[E0495]: cannot infer an appropriate lifetime for autoref due to conflicting requirements
--> src\grid.rs:208:44
|
208 | .map(|(ix, c)| S::step(c, self.get_neighbors(ix)))
| ^^^^^^^^^^^^^
|
note: first, the lifetime cannot outlive the anonymous lifetime #1 defined on the method body at 204:5...
--> src\grid.rs:204:5
|
204 | / fn make_diffs(&self) -> Vec<ManuallyDrop<(S::Diff, S::MoveNeighbors)>> {
205 | | self.cells[..]
206 | | .par_iter()
207 | | .enumerate()
... |
210 | | .collect()
211 | | }
| |_____^
note: ...so that reference does not outlive borrowed content
--> src\grid.rs:208:39
|
208 | .map(|(ix, c)| S::step(c, self.get_neighbors(ix)))
| ^^^^
note: but, the lifetime must be valid for the lifetime 'a as defined on the impl at 183:1...
--> src\grid.rs:183:1
|
183 | / impl<'a, S, C, D, M, N, MN> SquareGrid<S>
184 | | where
185 | | S: Sim<Cell = C, Diff = D, Move = M, Neighbors = N, MoveNeighbors = MN>,
186 | | S::Cell: Sync + Send,
... |
226 | | }
227 | | }
| |_^
= note: ...so that the types are compatible:
expected neighborhood::GetNeighbors<'_, usize, N>
found neighborhood::GetNeighbors<'a, usize, N>
/// Defines a simulation for complicated things that have too much state to abandon on the next cycle.
///
/// This enforces a rule in that all new cells are only produced from old board state. This prevents the
/// update order from breaking the simulation.
pub trait Sim {
/// The type of cells on the grid
type Cell;
/// Represents all information necessary to modify a cell in the previous grid to produce the version in the next
type Diff;
/// Data that moves between cells
type Move;
/// Neighborhood of cells.
type Neighbors;
/// Nighborhood of moving data
type MoveNeighbors;
/// Performs one step of the simulation.
fn step(&Self::Cell, Self::Neighbors) -> (Self::Diff, Self::MoveNeighbors);
/// Updates a cell with a diff and movements into this cell.
fn update(&mut Self::Cell, Self::Diff, Self::MoveNeighbors);
}
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment