Rust中向接收&[i32]的函数传入Vec引用为何能正常运行?
Rust 中 Vec 引用可直接传入切片参数的原理
你的猜测是正确的,这是Rust内置的解引用强制转换(Deref coercion) 特性提供的合法隐式类型转换能力,具体实现机制如下:
基础前提
你最初对fn1的参数类型存在认知偏差:&[i32]不是固定长度数组的引用(i32数组引用的语法为&[i32; N],N为数组的固定长度),而是i32类型的动态长度切片引用。
Deref trait 的实现约定
Rust 标准库中的Vec<T>容器实现了Deref trait,其关联类型Target被指定为[T],deref方法的实现会返回Vec内部存储元素的连续切片视图,等效于如下简化逻辑:
impl<T> Deref for Vec<T> { type Target = [T]; fn deref(&self) -> &Self::Target { // 基于Vec内部的指针和长度生成对应切片 unsafe { std::slice::from_raw_parts(self.as_ptr(), self.len()) } } }
自动转换触发规则
当以下条件全部满足时,Rust编译器会自动执行隐式类型转换,无需开发者手动编写转换代码:
- 实际传入的参数是类型
A的引用(即&A) - 函数要求的入参是类型
B的引用(即&B) - 类型
A实现了Deref<Target = B>
对应到你的示例场景:
- 你传入
fn1的实际参数是&Vec<i32>,即A为Vec<i32> fn1要求的入参是&[i32],即B为[i32]Vec<i32>实现了Deref<Target = [i32]>,完全符合转换规则
编译器会自动完成&Vec<i32> -> &[i32]的转换,等效于你手动编写fn1(&*my_vec):先解引用&my_vec得到Vec<i32>实例,再调用deref方法得到切片引用&[i32]。
同类常见转换场景
这种隐式转换是Rust中非常常用的设计,典型场景包括:
&String自动转换为&str:String实现了Deref<Target = str>&Box<T>自动转换为&T:Box<T>实现了Deref<Target = T>&Rc<T>/&Arc<T>自动转换为&T:对应智能指针均实现了Dereftrait
内容的提问来源于stack exchange,提问作者Kanwar Baweja
相关产品推荐
相关产品推荐

