我有一个使用奇怪重复模板模式的代码库,带有一个基类和一个派生类。
在接受基类参数的某个方法中,我想检查我收到的参数是否为派生类型,但我无法强制转换为它。
这是一个说明问题的示例:
class Base<T> where T : Base<T> {
}
class Derived<T> : Base<T>
where T : Derived<T> {
}
class DerivedBanana : Derived<DerivedBanana> {
}
class Program {
static void DoSomething<T>(T t) where T : Base<T> {
// CS0311: The type 'T' cannot be used as type parameter 'T' in the generic type or method 'Derived<T>'.
// There is no implicit reference conversion from 'T' to 'Derived<T>'.
var d = t as Derived<T>;
}
static void Main(string[] args) {
DoSomething(new DerivedBanana());
}
}
Run Code Online (Sandbox Code Playgroud)
DoSomething
如果T
我得到的参数实际上是 a ,有没有办法检查我的方法Derived<T>
?
注意:我正在重构我的代码以避免这种情况,但我仍然想知道如何进行这样的转换:)
注2:建议的重复不回答我的问题:我想知道如何投给派生类型,而不仅仅是检查变量是派生类型。
如果我得到的 T 参数实际上是派生参数,有没有办法可以检查我的 DoSomething 方法?
该类Derived<T>
可能会Base<T>
受到类型安全性较弱形式的限制
public class Base<T> where T : Base<T>
{
public virtual Base<T> This(){
return this as T;
}
}
public class Derived<T> : Base<T>
where T: Base<T>
{
public override Derived<T> This()
{
return base.This() as Derived<T>;
}
}
class DerivedBanana : Derived<DerivedBanana>
{
}
class BaseBanana : Base<BaseBanana>
{
}
class Program
{
static void DoSomething<T>(T t) where T : Base<T>
{
T d = (T)(t.This() as Derived<T> ?? t.This() as Base<T>);
Console.WriteLine(d.GetType());
}
static void Main(string[] args)
{
DoSomething(new BaseBanana());
DoSomething(new DerivedBanana());
}
}
Run Code Online (Sandbox Code Playgroud)