Compartir con Arc y Mutex
Modifique el estado compartido de forma segura
Compartir con Arc y Mutex es una lección gratuita de Learn Rust Coding en CoddyKit. Esta es la lección 3 de 4. Puedes leer la lección completa abajo gratuitamente — luego la practicas en el navegador con un editor de código integrado y un tutor de IA 24/7. Forma parte de la ruta de aprendizaje de Learn Rust Coding, y tu progreso se sincroniza en la web y la app de CoddyKit. El curso de Learn Rust Coding incluye 4 lecciones en total.
La necesidad de un estado compartido
A veces varios hilos deben leer o actualizar los mismos datos. Transferir la propiedad a un solo hilo no es suficiente.
Rust proporciona propiedad compartida segura entre hilos con Arc y mutación segura con Mutex. Juntos permiten usar un estado mutable compartido.
Arc: conteo atómico de referencias
Arc significa conteo atómico de referencias. Es similar a Rc, pero su contador usa operaciones atómicas, por lo que es seguro entre hilos.
Clonar un Arc no copia los datos. Solo incrementa el contador y devuelve otro handle al mismo valor.
use std::sync::Arc;
fn main() {
let shared = Arc::new(vec![1, 2, 3]);
let clone = Arc::clone(&shared);
println!("{:?} {:?}", shared, clone);
}Compartir Arc entre hilos
Para compartir datos de solo lectura, clone el Arc una vez por hilo y mueva cada copia al hilo correspondiente. Todos los hilos apuntan a la misma asignación.
Como Arc implementa Send y Sync, esto compila sin problemas.
use std::sync::Arc;
use std::thread;
fn main() {
let data = Arc::new(vec![10, 20, 30]);
let mut handles = vec![];
for i in 0..3 {
let d = Arc::clone(&data);
handles.push(thread::spawn(move || println!("{}", d[i])));
}
for h in handles { h.join().unwrap(); }
}Arc por sí solo solo permite leer
Arc proporciona propiedad compartida, pero solo acceso compartido e inmutable al valor interno.
No puede modificar datos directamente a través de un Arc, porque varios hilos podrían tenerlo a la vez y provocar una condición de carrera. Necesita mutabilidad interior con un bloqueo.
Mutex: exclusión mutua
Un Mutex protege los datos para que solo un hilo pueda acceder a ellos a la vez. Debe llamar a lock para obtener acceso.
lock devuelve un Result; al desenvolverlo obtiene un guard inteligente. Los demás hilos se bloquean hasta que el guard se descarta.
use std::sync::Mutex;
fn main() {
let m = Mutex::new(0);
{
let mut guard = m.lock().unwrap();
*guard += 5;
}
println!("{:?}", m);
}El guard y RAII
El valor que devuelve lock es un MutexGuard. Puede acceder a los datos internos desreferenciándolo con *.
Cuando el guard sale de su ámbito, el bloqueo se libera automáticamente. Este estilo RAII evita olvidar desbloquear.
Combinar Arc y Mutex
Para compartir un estado mutable entre hilos, envuelva un Mutex dentro de un Arc. Arc comparte la propiedad; Mutex protege la mutación.
Este patrón, Arc<Mutex<T>>, es la forma estándar de gestionar un estado mutable compartido en Rust.
use std::sync::{Arc, Mutex};
fn main() {
let counter = Arc::new(Mutex::new(0));
let c = Arc::clone(&counter);
*c.lock().unwrap() += 1;
println!("{}", *counter.lock().unwrap());
}Un contador compartido
Aquí, diez hilos incrementan cada uno un contador compartido. Cada uno clona el Arc, bloquea el Mutex y suma uno.
Como el bloqueo serializa el acceso, el total final siempre es exactamente diez.
use std::sync::{Arc, Mutex};
use std::thread;
fn main() {
let counter = Arc::new(Mutex::new(0));
let mut handles = vec![];
for _ in 0..10 {
let c = Arc::clone(&counter);
handles.push(thread::spawn(move || {
*c.lock().unwrap() += 1;
}));
}
for h in handles { h.join().unwrap(); }
println!("{}", *counter.lock().unwrap());
}Mantener brechas críticas cortas
El código que se ejecuta mientras se mantiene un bloqueo constituye la sección crítica. Los demás hilos esperan ahí, por lo que debe ser corta.
Bloquee, realice la actualización mínima y libere el bloqueo. Evite cálculos pesados o operaciones de E/S mientras lo mantiene.
use std::sync::Mutex;
fn main() {
let m = Mutex::new(Vec::new());
{
let mut v = m.lock().unwrap();
v.push(1);
} // lock released here
println!("{:?}", m.lock().unwrap());
}Deadlocks y poisoning
Si un hilo bloquea el mismo Mutex dos veces, o dos hilos bloquean dos mutexes en órdenes opuestos, puede producirse un deadlock y el programa quedar bloqueado indefinidamente.
Si un hilo produce un panic mientras mantiene un bloqueo, el Mutex queda envenenado y las llamadas posteriores a lock devuelven un Err.
RwLock para muchos lectores
Cuando las lecturas superan ampliamente a las escrituras, RwLock puede ser mejor que Mutex. Permite muchos lectores simultáneos o un único escritor exclusivo.
Use read para el acceso compartido y write para el acceso exclusivo.
use std::sync::RwLock;
fn main() {
let lock = RwLock::new(5);
{
let r = lock.read().unwrap();
println!("read {}", *r);
}
*lock.write().unwrap() += 1;
println!("{}", *lock.read().unwrap());
}Comprobación rápida
Compruebe su comprensión de Arc y Mutex.
Resumen
Ha aprendido que Arc comparte la propiedad entre hilos mediante un conteo atómico de referencias, pero solo permite el acceso inmutable.
Un Mutex protege la mutación y proporciona un guard que libera el bloqueo al descartarse. Combínelos como Arc<Mutex<T>> para crear un estado mutable compartido, teniendo en cuenta los deadlocks y el poisoning.
A continuación unirá hilos y recopilará sus resultados.
Preguntas frecuentes
¿La lección «Compartir con Arc y Mutex» es gratis?
Sí — el texto completo de «Compartir con Arc y Mutex» es gratis para leer aquí en la web. Para practicarla de forma interactiva (editor de código integrado y tutor de IA 24/7) y desbloquear el resto del curso de Learn Rust Coding, actualiza a CoddyKit PRO. El curso de Learn Rust Coding incluye 4 lecciones en total.
¿Qué aprenderé en «Compartir con Arc y Mutex»?
Modifique el estado compartido de forma segura Practicas Learn Rust Coding con código real que ejecutas directamente en el navegador, y un tutor de IA 24/7 responde tus preguntas mientras trabajas en la lección.
¿Necesito experiencia previa para empezar Learn Rust Coding?
No se requiere experiencia previa. Learn Rust Coding en CoddyKit está estructurado para principiantes hasta estudiantes avanzados, así que puedes empezar aquí o desde el inicio y avanzar a tu ritmo. Esta es la lección 3 de 4.
¿Cuánto tiempo toma la lección «Compartir con Arc y Mutex»?
La mayoría de las lecciones de CoddyKit toman alrededor de 5–10 minutos. Cada una es compacta e interactiva, así que avanzas constantemente y retomas exactamente por donde dejaste en la web y la app.
¿Puedo escribir y ejecutar código en esta lección de Learn Rust Coding?
Sí. Cada lección de Learn Rust Coding incluye un editor de código integrado, así que escribes y ejecutas código real directamente en tu navegador y obtienes retroalimentación instantánea de IA — sin configuración local necesaria.
Todas las lecciones de este curso
- Crear hilos
- Mover datos a los hilos
- Compartir con Arc y Mutex
- Unir hilos y recopilar resultados