¿Cómo iterar elementos de un hashmap entre ellos mismos y permitir que sean mutables?
Así que tengo un hashmap que utiliza cadenas como claves y los valores son mi propia estructura para usuarios. Que son solo su nombre y posición.
pub struct User {
name: String,
x: i32,
y: i32
}
Ahora lo que quiero hacer es iterar sobre el hashmap llamado “users” y comprobar si las posiciones de dos usuarios están cerca, y luego separarlos.
for (key, userA) in self.users.iter_mut() {
for (key, userB) in self.users.iter_mut() {
// el código de colisión iría aquí
}
}
Esto causa un problema porque los usuarios son prestados dos veces como mutables. Pensé en solucionar este problema usando un mutex,
for (key, userA) in self.users.lock().unwrap().iter_mut() {
for (key, userB) in self.users.lock().unwrap().iter_mut() {
// el código de colisión iría aquí
}
}
y el código compila, pero causa un error en tiempo de ejecución más adelante cuando realmente agrego un usuario al mapa debido al segundo bucle, ya que si comento ese bucle, el código se ejecuta sin problemas. ¿Alguna idea de cómo podría escribir esto de manera diferente?
davy.ai
Como experto en TI especializado en Rust y reglas de préstamo, recomendaría usar un enfoque diferente para lograr tu objetivo de separar a dos usuarios si sus posiciones están cerca. Aquí tienes dos posibles soluciones:
Vec<user>
en lugar de unHashMap<string, user="">
.Si no necesitas acceder a los usuarios por sus claves, puedes utilizar un vector para almacenarlos en su lugar. Esto te permitirá iterar sobre el vector solo una vez, sin ningún problema de préstamo:
Ten en cuenta que utilizamos índices en lugar de referencias directamente para evitar problemas de préstamo.
RefCell
yRefMut
para tomar prestados los usuarios de manera más flexible.Si realmente necesitas usar un hashmap, puedes utilizar
RefCell
yRefMut
para tomar prestados los usuarios de manera más flexible. Esto te permite tomarlos prestados como inmutables o mutables según sea necesario, sin violar las reglas de préstamo de Rust:Ten en cuenta que necesitamos comparar las claves para evitar la autocolisión, ya que el mismo usuario podría tomarse prestado dos veces de esta manera.
En resumen, utilizando un
Vec<user>
oRefCell
yRefMut
, puedes evitar problemas de préstamo y lograr tu objetivo.</string,>