[Conceptos básicos de Rust] Rust Smart Pointer

prefacio

En Rust, un puntero inteligente es un tipo de puntero que proporciona una funcionalidad adicional. Los punteros inteligentes pueden verificar la seguridad de la memoria en tiempo de compilación y tiempo de ejecución, y proporcionar un modelo de propiedad y préstamo más flexible. Este blog presentará los punteros inteligentes en Rust en detalle, incluidos los tipos de punteros inteligentes de uso común, la creación y el uso de punteros inteligentes, la seguridad de la memoria y las consideraciones de rendimiento, etc.

Puntero inteligente de caja

Box es uno de los tipos de punteros inteligentes más simples proporcionados por Rust. Puede asignar memoria en el montón y liberar memoria cuando se transfiere la propiedad. Los punteros inteligentes de caja a menudo se usan para resolver el problema del tamaño indeterminado de los tipos recursivos en Rust.

Para crear un puntero inteligente Box, podemos usar Box::newla función para envolver el valor en un Box. Aquí hay un ejemplo que demuestra cómo crear y usar un puntero inteligente Box:

fn main() {
    
    
    let x = Box::new(5); // 创建一个 Box 指向整数 5
    println!("x = {}", x);
}

En el ejemplo anterior, usamos Box::newla función para crear un cuadro que apunte al número entero 5. Dado que Box es un puntero inteligente, liberará automáticamente la memoria cuando finalice el alcance.

El puntero inteligente de caja es un tipo de puntero ligero adecuado para la asignación dinámica y la transferencia de propiedad en la mayoría de los casos.

puntero inteligente rc

Rc es un tipo de puntero inteligente contado por referencia proporcionado por Rust. Permite que varios propietarios compartan el acceso a los mismos datos. Los punteros inteligentes Rc a menudo se usan en escenarios de propiedad compartida para datos inmutables.

Para crear un puntero inteligente Rc, podemos usar Rc::newla función para envolver el valor en Rc. Aquí hay un ejemplo que demuestra cómo crear y usar un puntero inteligente Rc:

use std::rc::Rc;

fn main() {
    
    
    let shared_data = Rc::new("Hello, world!"); // 创建一个 Rc 指向字符串
    println!("Length: {}", shared_data.len());

    let cloned_data = Rc::clone(&shared_data); // 克隆 Rc 指针
    println!("Reference count: {}", Rc::strong_count(&cloned_data));
}

En el ejemplo anterior, usamos Rc::newla función para crear un puntero Rc a una cadena. Luego usamos Rc::clonela función para clonar el puntero Rc y usamos Rc::strong_countla función para obtener el recuento de referencia.

Los punteros inteligentes Rc utilizan el conteo de referencias para rastrear la propiedad de los datos compartidos. Cuando el conteo de referencia llega a cero, la memoria se libera.

Punteros inteligentes Mutex y RwLock

Mutex y RwLock son tipos de punteros inteligentes proporcionados por Rust para la sincronización de subprocesos múltiples. Permiten que el acceso a los datos se comparta de forma segura entre varios subprocesos.

Mutex es un bloqueo de exclusión mutua que proporciona acceso exclusivo. Para crear un puntero inteligente Mutex, podemos usar Mutex::newla función. Aquí hay un ejemplo que demuestra cómo crear y usar un puntero inteligente Mutex:

use std::sync::Mutex;

fn main() {
    
    
    let data = Mutex::new(0); // 创建一个 Mutex 包装的整数
    let mut value = data.lock().unwrap();
    *value += 1;
    println!("Value: {}", *value);
}

En el ejemplo anterior, usamos Mutex::newla función para crear un puntero inteligente Mutex que envuelve un número entero. Luego usamos lockel método para tomar posesión del mutex y unwrapdesenredar el resultado usando el . Finalmente, incrementamos el entero e imprimimos el resultado.

RwLock es un bloqueo de lectura y escritura que proporciona múltiples accesos de solo lectura o un acceso de escritura exclusivo. Para crear un puntero inteligente RwLock, podemos usar RwLock::newla función.

Mutex y RwLock proporcionan métodos de acceso de subprocesos múltiples flexibles y seguros, que pueden garantizar la consistencia y corrección de los datos en un entorno concurrente.

puntero inteligente personalizado

En Rust, también podemos crear nuestros propios punteros inteligentes implementando tipos personalizados. Los punteros inteligentes personalizados se utilizan a menudo para proporcionar una gestión de memoria y una semántica específicas.

Para crear punteros inteligentes personalizados, debemos implementar características como y para proporcionar un comportamiento de puntero y una lógica de liberación de memoria Deref.Drop

Aquí hay un ejemplo que muestra cómo crear un puntero inteligente personalizado simple:

use std::ops::Deref;

struct MyBox<T>(T);

impl<T> MyBox<T> {
    
    
    fn new(x: T) -> MyBox<T> {
    
    
        MyBox(x)
    }
}

impl<T> Deref for MyBox<T> {
    
    
    type Target = T;

    fn deref(&self) -> &Self::Target {
    
    
        &self.0
    }
}

fn main() {
    
    
    let x = MyBox::new(5);
    println!("x = {}", *x);
}

En el ejemplo anterior, creamos un MyBoxtipo de puntero inteligente personalizado llamado . Este tipo envuelve un valor genérico e implementa Derefcaracterísticas para proporcionar un comportamiento de puntero.

Al implementar Derefel rasgo, podemos usar *el operador para desreferenciar punteros inteligentes personalizados.

Consideraciones de seguridad y rendimiento de la memoria

Al usar punteros inteligentes, debemos prestar atención a las consideraciones de seguridad y rendimiento de la memoria.

Una gran ventaja de los punteros inteligentes es que la seguridad de la memoria se comprueba en el momento de la compilación. Por ejemplo, los punteros inteligentes de Box garantizan que la memoria en el montón se libere correctamente en el momento de la compilación, lo que evita errores de memoria comunes, como punteros nulos y punteros perdidos.

Por otro lado, los punteros inteligentes pueden generar cierta sobrecarga de rendimiento. Por ejemplo, los punteros inteligentes de conteo de referencia (como Rc) deben mantener los conteos de referencia en tiempo de ejecución, lo que puede generar una sobrecarga adicional. Por lo tanto, en escenarios sensibles al rendimiento, es posible que debamos sopesar el costo y el beneficio de usar punteros inteligentes.

Al elegir un puntero inteligente, debemos considerar exhaustivamente todos los aspectos de la seguridad de la memoria, el rendimiento y el diseño del código de acuerdo con los escenarios y las necesidades específicas.

Resumir

Este blog presenta los punteros inteligentes en Rust en detalle, incluidos Box, Rc, Mutex, RwLock y punteros inteligentes personalizados. Los punteros inteligentes son una de las herramientas poderosas de Rust que brindan seguridad de memoria, flexibilidad en los modelos de propiedad y préstamo, y soporte para el acceso simultáneo en un entorno de subprocesos múltiples.

Espero que este blog lo ayude a comprender y aplicar sugerencias inteligentes en Rust. ¡Gracias por leer!

Supongo que te gusta

Origin blog.csdn.net/qq_21484461/article/details/131731268
Recomendado
Clasificación