为什么这两个代码示例相等?引用之间的差异,借用的变量,指针


fn largest(num_list: &[i32]) -> i32 {
let mut largest = num_list[0];
for &num in num_list {
if num > largest {
largest = num
}
}
largest
}
fn largest2(num_list: &[i32]) -> i32 {
let mut largest = num_list[0];
for num in num_list {
if num > &largest {
largest = *num
}
}
largest
}
fn main() {
let num_list = vec![30, 20, 10, 60, 50, 40];
let largest = largest(&num_list);
let largest2 = largest2(&num_list);
println!("The largest number in num_list fn is: {}.", largest);
println!("The largest number in num_list fn is: {}.", largest2);
}

可以看到最大的有一些细微的差异largest2。有人能帮助我理解这里的差异,为什么两个代码样本实际上功能相同?

两个示例之间的主要区别源于您的循环语句,for num in num_listvsfor &num in num_list。首先,重要的是要理解它们等价于for [...] in num_list.iter(),即它们迭代num_list元素的引用。然后将这些类型为&i32的引用赋值给num&num。在第一种情况下,我们只有一个直接赋值,因此是num: &i32。在第二种情况下,有一个不可辩驳的赋值,将num绑定到数字,因此是num: i32。顺便说一句,这是可能的,因为即使你试图从借用,i32: Copy移出一个值,所以Rust编译它很好。

剩下的只是适应:要么你使用&i32,要么直接使用i32。例如,当num: &i32largest比较时,你应该取消对num的引用,然后再比较,得到*num > largest。然而,num > &largest也可以工作,因为Rust知道如何通过解引用来比较两个&i32(因此它实际上会生成*num > largest)。同样地,当你给largest赋值时,你必须赋值一个i32,所以你取消对num:largest = *num的引用。

这很容易理解,为什么这两段代码做同样的事情:在一个版本中,您将指针的值复制到num中的整数,然后使用它,而在另一个版本中,您保留num中的解引用,每次需要使用它时只需解引用它。

相关内容

  • 没有找到相关文章

最新更新