用Rust實現單例

张疯牛發表於2024-04-28

1. 使用Arc + Mutex

在這個例子中,我們使用了 Arc (原子引用計數)和 Mutex (互斥鎖)來實現執行緒安全的單例。透過 get_instance 方法,我們可以獲取到單例例項,並對例項進行操作。

use std::sync::{Arc, Mutex};

struct Singleton {
    // 單例資料
    data: String,
}

impl Singleton {
    // 獲取單例例項的方法
    fn get_instance() -> Arc<Mutex<Singleton>> {
        // 使用懶載入建立單例例項
        // 這裡使用了 Arc 和 Mutex 來實現執行緒安全的單例
        // 只有第一次呼叫 get_instance 時會建立例項,之後都會返回已建立的例項
        static mut INSTANCE: Option<Arc<Mutex<Singleton>>> = None;
        unsafe {
            INSTANCE
                .get_or_insert_with(|| {
                    Arc::new(Mutex::new(Singleton {
                        data: String::from("Singleton instance"),
                    }))
                })
                .clone()
        }
    }
}

fn main() {
    // 獲取單例例項
    let instance1 = Singleton::get_instance();
    let instance2 = Singleton::get_instance();
    // 修改單例資料
    {
        let mut instance = instance1.lock().unwrap();
        instance.data = String::from("Modified singleton instance");
    }
    // 輸出單例資料
    {
        let instance = instance2.lock().unwrap();
        println!("{}", instance.data);
    }
}

2. 使用lazy_static的懶載入

使用 lazy_static crate: lazy_static crate 是一個常用的 Rust crate,可以實現懶載入的全域性靜態變數。透過 lazy_static ,可以在需要時建立單例例項,並確保只有一個例項被建立:

use lazy_static::lazy_static;
   use std::sync::Mutex;
    struct Singleton {
       // 單例資料
       data: String,
   }
    lazy_static! {
       static ref INSTANCE: Mutex<Singleton> = Mutex::new(Singleton {
           data: String::from("Singleton instance"),
       });
   }
    fn main() {
       // 獲取單例例項
       let instance = INSTANCE.lock().unwrap();
       println!("{}", instance.data);
   }

3. 使用once_cell crate

使用 once_cell crate: once_cell crate 是另一個常用的 Rust crate,可以實現懶載入的全域性靜態變數。透過 once_cell ,可以在首次訪問時建立單例例項,並確保只有一個例項被建立:

use once_cell::sync::Lazy;
    struct Singleton {
       // 單例資料
       data: String,
   }
    static INSTANCE: Lazy<Singleton> = Lazy::new(|| Singleton {
       data: String::from("Singleton instance"),
   });
    fn main() {
       // 獲取單例例項
       let instance = INSTANCE.clone();
       println!("{}", instance.data);
   }

4. 使用 Rc 和 RefCell

使用 Rc 和 RefCell : Rc 是 Rust 標準庫中的引用計數型別, RefCell 是一個提供內部可變性的型別。結合使用 Rc 和 RefCell ,可以實現簡單的單例模式:

use std::rc::Rc;
   use std::cell::RefCell;
    struct Singleton {
       // 單例資料
       data: String,
   }
    fn main() {
       // 建立單例例項
       let instance = Rc::new(RefCell::new(Singleton {
           data: String::from("Singleton instance"),
       }));
        // 獲取單例例項
       let borrowed_instance = instance.borrow();
       println!("{}", borrowed_instance.data);
   }    

原文:https://blog.csdn.net/u013769320/article/details/132094193

相關文章