026 Rust死灵书之实现Vec

介绍

本系列录制的视频主要放在B站上Rust死灵书学习视频

Rust 死灵书相关的源码资料在github.com/anonymousGiga/Rustonomi...

从本节开始,我们用我们在Rust死灵书中学到的知识实现一个Vec。

MyVec的初始定义

我们的Vec的定义只要这样就可以了:

pub Struct MyVec<T> {
    ptr: *mut T,
    cap: usize,
    len: usize,
}

如此定义的问题: 我们此处使用的裸指针ptr其实是想达到可变引用的效果,从安全的角度,不应该有别名,或者通俗一点说,此处我们应该锁定它的内容和owner。

因此,我们定义一个Unique类型,让裸指针拥有数据。

优化的Vec定义

Uninque类型定义

Unique类型应该满足的条件:

  • 对T可变;
  • 拥有类型T的值(用于drop检查);
  • 如果T是Send/Sync,那Unique就也是Send/Sync的;
  • 指针永远不为null。

可能的Unique定义如下:

use std::marker::PhantomData;

//1、结构体的定义满足前两点
struct Unique<T> {
    ptr: *const T, //指针不可变,指针指向的内容可变
    _marker: PhantomData<T>, //用于drop检查,如果不加,编译器会认为,结构体没有拥有类型T,调不调用析构函数都无所谓
}

//2、满足第三点
unsafe impl<T: Send> Send for Unique<T> {}
unsafe impl<T: Sync> Sync for Unique<T> {}

impl<T> Unique<T> {
    const unsafe fn new_unchecked(ptr: *mut T) -> Self {
        unsafe { Unique { ptr: ptr, _marker: PhantomData} }
    }

    //3、满足第四点
    fn new(ptr: *mut T) -> Option<Self> {
        if !ptr.is_null() {
            Some(unsafe { Unique { ptr: ptr, _marker: PhantomData} })
        } else {
            None
        }
    }

    fn as_ptr(&self) -> *mut T {
        self.ptr as *mut T
    }
}

新的Vec定义

pub struct MyVec<T> {
    //ptr: *mut T,
    ptr: Unique<T>,
    cap: usize,
    len: usize,
}
本作品采用《CC 协议》,转载必须注明作者和本文链接
令狐一冲
讨论数量: 0
(= ̄ω ̄=)··· 暂无内容!

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!