为了定义泛型版本的 largest 函数,类型参数声明位于函数名称与参数列表中间的尖括号 中,像这样:
fn largest<T>(list: &[T]) -> &T {
复制代码
一个使用泛型参数的 largest 函数定义:
//函数 largest 有泛型类型 T,//有个参数 list,其类型是元素为 T 的 slice//largest 函数会返回一个与 T 相同类型的引用fn largest<T>(list: &[T]) -> &T { let mut largest = &list[0]; for item in list { if item > largest { largest = item; } } largest}fn main() { //标准库为 i32 和 char 实现了 PartialOrd let number_list = vec![34, 50, 25, 100, 65]; let result = largest(&number_list); println!("The largest number is {}", result); let char_list = vec!['y', 'm', 'a', 'q']; let result = largest(&char_list); println!("The largest char is {}", result);}
复制代码
为了开启比较功能,标准库中定义的 std::cmp:artialOrd trait 可以实现类型的比较功能,限制 T 只对实现了 PartialOrd 的类型有效否则代码会编译错误。
结构体定义中的泛型
可以用 语法来定义结构体,它包含一个或多个泛型参数类型字段。
Point 结构体存放了两个 T 类型的值 x 和 y:
记住通过在函数签名中指定生命周期参数时,并没有改变任何传入值或返回值的生命周期,而是指出任何不满足这个约束条件的值都将被借用检查器拒绝。 注意: longest 函数并不需要知道 x 和 y 具体会存在多久,而只需要知道有某个可以被 'a 替代的作用域将会满足这个签名。
当具体的引用被传递给 longest 时,泛型生命周期 'a 的具体生命周期等同于 x 和 y 的生命周期中较小的那一个。
通过拥有不同的具体生命周期的 String 值调用 longest 函数:
fn main() {
let string1 = String::from("long string is long");
{
let string2 = String::from("xyz");
let result = longest(string1.as_str(), string2.as_str());
//能够编译和运行,并打印出 The longest string is long string is long
println!("The longest string is {}", result);
}
}
复制代码
尝试在 string2 离开作用域之后使用 result,不能编译:
fn main() {
let string1 = String::from("long string is long");
let result;
{
let string2 = String::from("xyz");
result = longest(string1.as_str(), string2.as_str());