ARTICLE DETAIL

资讯详情

深耕网站建设、视觉设计与SEO优化的一线实战洞察。

rust Sized trait什么意思

rust Sized trait什么意思 在 Rust 中Sizedtrait 是一个非常基础且重要的 trait它标志着类型的大小在编译时是已知的。简单来说绝大多数类型都是Sized的而“不定长类型”DST则不是。下面从几个方面来深入理解1. 隐式约束默认行为Rust 中泛型类型参数默认带有Sized约束。这意味着如果你写rustfn exampleT(x: T) { // ... }编译器实际认为你写的是rustfn exampleT: Sized(x: T) { // ... }这表示参数x必须是一个编译时就知道确切大小的类型比如i32、f64、或者结构体实例这样才能在栈上分配内存或安全地传参。2. 什么时候类型不是Sized即?Sized有三类常见的类型不满足Sized即大小不定切片Slice如[u8]注意不是[u8]引用的大小是固定的。Trait 对象dyn Trait如dyn Iterator因为具体实现的大小未知。结构体的最后一个字段如果是 DST那么这个结构体本身也会变成 DST。如果你想让泛型参数能接受这些“不定长”类型就需要使用?Sized来“解除”默认的Sized约束rustfn exampleT: ?Sized(x: T) { // 注意通常通过引用或指针传递 // ... }3. 为什么需要Sized因为编译器需要知道如何为变量分配内存栈分配局部变量默认在栈上栈要求固定大小。传参函数参数默认按值传递需要知道大小。对于非Sized类型DST你无法直接将其作为变量或参数而是必须通过指针引用、Box、Rc等来间接访问因为指针的大小是固定的例如[u8]在 64 位系统上是 16 字节包含了指针和长度。4. 实际代码示例错误写法编译不通过rustfn bad(x: [u8]) { } // 错误[u8] 的大小在编译时未知正确写法通过引用rustfn good(x: [u8]) { } // 正常因为 [u8] 是 Sized泛型中的使用rust// 默认只能用于 Sized 类型 fn func1T(a: T) { } // 可以用于任意类型包括 DST但必须通过引用 fn func2T: ?Sized(a: T) { } fn main() { func1(3i32); // OK // func1([1,2,3] as [u8]); // 尝试传 DST 会报错 let slice: [u8] [1, 2, 3]; func2(slice); // OKT 被推导为 [u8]不定长通过引用传递 }5. 特殊的一点strvsstrstr是字符串切片是 DST不定长不是Sized。str是一个引用胖指针是Sized。这就是为什么函数参数我们总是用str而不是str。总结概念含义T: SizedT的大小在编译时已知默认情况。T: ?SizedT可以是Sized的也可以不是用于放宽限制。DST 例子[u8]、dyn Trait、str。如何操作 DST必须通过指针、Box、Rc等。如果你在定义数据结构时想让字段存储不定长数据比如 trait 对象通常需要加上?Sized约束并配合指针使用最常见的就是Boxdyn Trait。如果还有关于Sized的具体应用场景比如自定义智能指针想深入探讨可以随时告诉我。
返回列表