[英]Cast a generic param to a specific type
如果我有两个结构:
struct A {...}
struct B {...}
和一个通用函数fn f<T>(param: T)
,我通过传递对A
或B
的引用调用它,在该函数中有没有办法拥有这样的东西(伪代码):
if param is A {
// do something with "param as A", like this:
let a: A = (A) param;
// ...
}
在 Java、C# 等语言中,我会简单地检查一个对象是否是A
的实例,如果是,则将其强制转换为A
如上例所示。 我怎样才能在 Rust 中做这样的事情? 我知道我可以在 trait 中加入一些特定于类型的逻辑,但我特别要求一种更简单、更直接的方法。
您可以使用Any
trait 的 trait 对象来完成您所要求的操作,例如
use std::any::Any;
#[derive(Debug)]
struct A;
#[derive(Debug)]
struct B;
fn foo(param: &dyn Any) {
if let Some(a) = param.downcast_ref::<A>() {
dbg!(a);
}
if let Some(b) = param.downcast_ref::<B>() {
dbg!(b);
}
}
但是,对于常见的用例,有更多地道、符合人体工程学和高效的解决方案。 您在问题中提到在A
和B
上实现一个共同特征,这是一种方法。 另一种方法是为您要支持的所有类型定义一个带有变体的枚举:
enum MyEnum {
A(A),
B(B),
}
fn bar(param: MyEnum) {
match param {
MyEnum::A(a) => { dbg!(a); },
MyEnum::B(b) => { dbg!(b); },
}
}
你正在寻找的东西在当前的 Rust 中还没有完全可用,但一旦专业化功能登陆就会可用。 使用专业化并在当前每晚可测试,您的函数将如下所示:
#![feature(min_specialization)]
struct A {}
struct B {}
fn f<T>(param: Vec<T>) {
trait Detect {
fn detect(&self);
}
impl<T> Detect for Vec<T> {
default fn detect(&self) {
println!("I am something else");
}
}
impl Detect for Vec<A> {
fn detect(&self) {
println!("I am a Vec<A>");
}
}
param.detect();
// ...
}
fn main() {
f(Vec::<A>::new());
f(Vec::<B>::new());
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.