Rust写时克隆Cow系列2,如何实现疑问?
摘要:细心的同学也许会发现,讲了Cow,那么Cow能够接受任意类型参数吗?咱先说答案,不可以。至于为什么呢?请同学们接着往下读。 在 Rust 中,Cow<'a, B>::Own
细心的同学也许会发现,讲了Cow,那么Cow能够接受任意类型参数吗?咱先说答案,不可以。至于为什么呢?请同学们接着往下读。
在 Rust 中,Cow<'a, B>::Owned变体接受的类型由泛型参数B决定,其约束规则非常明确:
1. 核心约束:ToOwned关联类型
Cow::Owned接受的数据类型必须是B类型关联的“拥有所有权”版本。
具体语法定义如下:
pub enum Cow<'a, B> where B: 'a + ToOwned + ?Sized {
Borrowed(&'a B),
Owned(<B as ToOwned>::Owned), // 接受的就是这个类型
}
这意味着Owned变体接受的类型必须实现std::borrow::ToOwned接口中的Owned类型。
2. 常见匹配关系表
在实际开发中,最常与Cow搭配的类型如下:
借用类型B(Borrowed)
Cow::Owned接受的类型示例场景
str
String
处理字符串,如Cow<'static, str>
[T](切片)
Vec<T>
处理列表数据
Path
PathBuf
处理文件路径
CStr
CString
处理 FFI 中的 C 字符串
T(已实现Clone)
T
任何实现Clone的普通结构体
3. 为什么不直接接受任意类型?
Cow(Copy-on-Write)的设计初衷是在需要修改数据时能从借用态转换为拥有态。
如果你传入一个自定义类型MyStruct给Cow::Owned,编译器要求必须存在一个对应的B类型,使得B::to_owned()能产生该MyStruct。
通常对于普通的Clone类型,B和Owned是同一种类型。
4. 变体即函数语法回顾
正如之前提到的,Cow::Owned本身也是一个构造函数。
let s = String::from("Hello");
// Cow::Owned 作为一个 fn(String) -> Cow<str> 的函数指针
let my_cow: Cow<str> = Cow::Owned(s);
参考资料:
1.Rust写时克隆Cow
2.Rust枚举变体详解
3.rust语言泛型实现
