Rust-rocksdb: Jadikan `cf_handle` bebas kunci

Dibuat pada 13 Mar 2019  ·  12Komentar  ·  Sumber: rust-rocksdb/rust-rocksdb

Fungsi cf_handle sering disebut sangat sering dan implementasinya memerlukan perolehan kunci baca ke peta yang mendasarinya. Jika ini disebut dalam hot-path, itu dapat memiliki implikasi kinerja. Kita harus menyelidiki pengalihan ini ke pendekatan yang tidak memerlukan kunci. Sebagai contoh, kita dapat membuat create_cf dan drop_cf dan fungsi lain yang mengubah peta internal memerlukan referensi yang dapat diubah ke DB dan membuat pemanggil bertanggung jawab untuk memperoleh kunci apa pun agar untuk mengubah DB .

Komentar yang paling membantu

Ya itu. Kami berencana untuk merilisnya dalam waktu dekat.

Semua 12 komentar

seperti ini?

use std::collections::HashMap;

#[derive(Debug)]
struct ColumnFamily(i32);

struct DB {
    cfs:HashMap<i32,ColumnFamily>,
}

impl DB {
    fn new()->DB{
        let mut cfs = HashMap::new();
        cfs.insert(1,ColumnFamily(1));
        cfs.insert(2,ColumnFamily(2));
        DB{
            cfs
        }
    }
    fn get(&self,key:i32)->&ColumnFamily{
        self.cfs.get(&key).unwrap()
    }
    fn drop_key(&mut self,key:i32){
        self.cfs.remove(&key);
    }
}

fn main() {
    let mut f = DB::new();
    let a = f.get(1);
    println!("{:?}",a);
    f.drop_key(1);
    let c = f.get(2);
    println!("{:?}",c);
}

FWIW, di garpu paritech cf_handle adalah Copy , yang secara teknis tidak aman (OTOH orang akan berpendapat sulit untuk disalahgunakan), tetapi menghindari penggunaan kunci.

@hjiayz Ya, sangat mirip dengan itu.

Ketika saya mencoba membuat perubahan ini (yaitu mengambil &mut self saat membuat/menjatuhkan keluarga kolom) saya mengalami masalah dengan cara mendefinisikan ColumnFamily . Ini akan menyimpan referensi yang bisa berubah di PhantomData yang membuat kode seperti ini gagal:

#[test]
fn property_cf_test() {
    let n = DBPath::new("_rust_rocksdb_property_cf_test");
    {
        let opts = Options::default();
        let mut db = DB::open_default(&n).unwrap(); // Notice the `mut`
        let cf = db.create_cf("cf1", &opts).unwrap();
        let value = db.property_value_cf(cf, "rocksdb.stats").unwrap().unwrap();

        assert!(value.contains("Stats"));
    }
}

Kesalahan terjadi ketika membuat panggilan metode pada db yang membutuhkan &self , seperti db.property_value_cf() dan meneruskan ColumnFamily (yang menyimpan &mut di db bidang):

error[E0502]: cannot borrow `db` as immutable because it is also borrowed as mutable
  --> tests/test_property.rs:39:21
   |
38 |         let cf = db.create_cf("cf1", &opts).unwrap();
   |                  -- mutable borrow occurs here
39 |         let value = db.property_value_cf(cf, "rocksdb.stats").unwrap().unwrap();
   |                     ^^                   -- mutable borrow later used here
   |                     |
   |                     immutable borrow occurs here

Saya tidak bisa memikirkan cara yang sangat elegan untuk mengatasi ini, tetapi satu opsi adalah tidak mengembalikan ColumnFamily dari create_cf dan alih-alih membiarkan kode yang dikonsumsi mengambilnya dengan panggilan ke cf_handle() :

#[test]
fn property_cf_test() {
    let n = DBPath::new("_rust_rocksdb_property_cf_test");
    {
        let opts = Options::default();
        let mut db = DB::open_default(&n).unwrap();
        db.create_cf("cf1", &opts).unwrap();
        let cf = db.cf_handle("cf1").unwrap(); // Get the CF
        let value = db.property_value_cf(cf, "rocksdb.stats").unwrap().unwrap();

        assert!(value.contains("Stats"));
    }
}

Apakah mengubah create_cf() untuk mengembalikan Result<(), Error> merupakan perubahan yang dapat diterima?

@dvdplm Menambahkan masa pakai ke ColumnFamily akhirnya menjadi sedikit mimpi buruk dari perspektif ergonomis. Saya ingin mengejar pendekatan yang tidak membutuhkan seumur hidup tetapi juga tidak mengambil risiko menggunakan penunjuk keluarga kolom setelah dihapus. Perubahan itu kemungkinan akan memengaruhi cara kami menghapus kunci dari cf_handle - Anda mungkin tidak akan melihat masalah ini.

Setuju dengan @iSynaptic. Jelas mengembalikan referensi ke ColumnFamily adalah cara yang aman hanya dalam kasus ini.

Mungkin #298 bisa digabung?

314

Apakah diselesaikan dengan # 314? Ada rencana untuk rilis jika demikian?

Ya itu. Kami berencana untuk merilisnya dalam waktu dekat.

@aleksuss apa status

@bkchr Saya pikir kami akan melakukannya minggu depan.

Apakah halaman ini membantu?
0 / 5 - 0 peringkat

Masalah terkait

elichai picture elichai  ·  6Komentar

benoitc picture benoitc  ·  7Komentar

zach-schoenberger picture zach-schoenberger  ·  7Komentar

mvines picture mvines  ·  10Komentar

iSynaptic picture iSynaptic  ·  31Komentar