多态性、继承和泛型 C#:无法将子类转换为超类型
Polymorphism, inheritance and generic C# : Cannot cast subclass into supertype
我对 c# 中的抽象 class 和泛型有疑问(我通常在 Java 中编码):这是我想使用的代码:
public interface InterfaceResult {...}
public abstract class Result : InterfaceResult {...}
public class ResultA : Result {...}
public class ResultB : Result {...}
public interface InterfaceKing { InterfaceResult function();}
public abstract class King : InterfaceKing {
public abstract Result function();
}
public class KingA : King {
public override ResultA function(){...}
}
public class KingB : King {
public override ResultB function(){...}
}
但这行不通:Visual Studio 想要 KingA 和 KingB return 带有 function() 的 Result 实例。如果我使用 "new" 而不是覆盖,VS 说我没有实现所需的方法(我需要使用覆盖)。
所以我尝试了通用的,但并没有更好
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing<T> {T function(); }
public abstract class King<Result> : IKing<Result>
{
public abstract Result function();
public static implicit operator King<Result>(KingB v)
{
return v; // generate Whosebug Exception
}
public static implicit operator King<Result>(KingA v)
{
throw new NotImplementedException();
}
}
public class KingA : King<ResultA>
{
public override ResultA Get()
{
return new ResultA();
}
}
public class KingB : King<ResultB>
{
public override ResultB Get()
{
return new ResultB();
}
}
public class Test
{
King<Result> a = new KingA(); // allowed by public static implicit operator King<Result>(KingA v)
King<Result> b = new KingB(); // allowed by public static implicit operator King<Result>(KingB v)
KingA ka = new KingA();
List<King<Result>> lista = new List<King<Result>>();
public void test()
{
lista.Add(ka);
}
}
我怎样才能完成这项工作?我找不到任何解决方案,也找不到任何好的或完整的示例。
从 "full interface" 移动到 "no interface"(因为缺少更好的术语)所有这些工作(这个 Main 工作正常)
static void Main ()
{
King a = new KingA ();
King b = new KingB ();
KingA ka = new KingA ();
List<King> list = new List<King> ();
list.Add (a);
list.Add (b);
list.Add (ka);
}
"full interface"
public interface InterfaceResult { }
public abstract class Result : InterfaceResult { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface InterfaceKing { InterfaceResult Function (); }
public abstract class King : InterfaceKing
{
public abstract InterfaceResult Function ();
}
public class KingA : King
{
public override InterfaceResult Function () => new ResultA ();
}
public class KingB : King
{
public override InterfaceResult Function () => new ResultA ();
}
"mixed (less interface)"
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing { Result Function (); }
public abstract class King : IKing
{
public abstract Result Function ();
}
public class KingA : King
{
public override Result Function () => new ResultA ();
}
public class KingB : King
{
public override Result Function () => new ResultB ();
{
return new ResultB ();
}
}
"no interface"
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public abstract class King
{
public abstract Result Function ();
}
public class KingA : King
{
public override Result Function () => new ResultA ();
}
public class KingB : King
{
public override Result Function () => new ResultB ();
}
使用协方差
参见 .net fiddler here. Read more about Covariance and Contravariance
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing<out T> where T : Result {}
public abstract class King<T> : IKing<T> where T : Result
{
public abstract T Get();
}
public class KingA : King<ResultA>
{
public override ResultA Get()
{
return new ResultA();
}
}
public class KingB : King<ResultB>
{
public override ResultB Get()
{
return new ResultB();
}
}
public class TestClass
{
King<ResultA> a = new KingA(); // allowed by public static implicit operator King<Result>(KingA v)
King<ResultB> b = new KingB(); // allowed by public static implicit operator King<Result>(KingB v)
KingA ka = new KingA();
List<IKing<Result>> lista = new List<IKing<Result>>();
public void Test()
{
lista.Add(ka);
}
}
我对 c# 中的抽象 class 和泛型有疑问(我通常在 Java 中编码):这是我想使用的代码:
public interface InterfaceResult {...}
public abstract class Result : InterfaceResult {...}
public class ResultA : Result {...}
public class ResultB : Result {...}
public interface InterfaceKing { InterfaceResult function();}
public abstract class King : InterfaceKing {
public abstract Result function();
}
public class KingA : King {
public override ResultA function(){...}
}
public class KingB : King {
public override ResultB function(){...}
}
但这行不通:Visual Studio 想要 KingA 和 KingB return 带有 function() 的 Result 实例。如果我使用 "new" 而不是覆盖,VS 说我没有实现所需的方法(我需要使用覆盖)。
所以我尝试了通用的,但并没有更好
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing<T> {T function(); }
public abstract class King<Result> : IKing<Result>
{
public abstract Result function();
public static implicit operator King<Result>(KingB v)
{
return v; // generate Whosebug Exception
}
public static implicit operator King<Result>(KingA v)
{
throw new NotImplementedException();
}
}
public class KingA : King<ResultA>
{
public override ResultA Get()
{
return new ResultA();
}
}
public class KingB : King<ResultB>
{
public override ResultB Get()
{
return new ResultB();
}
}
public class Test
{
King<Result> a = new KingA(); // allowed by public static implicit operator King<Result>(KingA v)
King<Result> b = new KingB(); // allowed by public static implicit operator King<Result>(KingB v)
KingA ka = new KingA();
List<King<Result>> lista = new List<King<Result>>();
public void test()
{
lista.Add(ka);
}
}
我怎样才能完成这项工作?我找不到任何解决方案,也找不到任何好的或完整的示例。
从 "full interface" 移动到 "no interface"(因为缺少更好的术语)所有这些工作(这个 Main 工作正常)
static void Main ()
{
King a = new KingA ();
King b = new KingB ();
KingA ka = new KingA ();
List<King> list = new List<King> ();
list.Add (a);
list.Add (b);
list.Add (ka);
}
"full interface"
public interface InterfaceResult { }
public abstract class Result : InterfaceResult { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface InterfaceKing { InterfaceResult Function (); }
public abstract class King : InterfaceKing
{
public abstract InterfaceResult Function ();
}
public class KingA : King
{
public override InterfaceResult Function () => new ResultA ();
}
public class KingB : King
{
public override InterfaceResult Function () => new ResultA ();
}
"mixed (less interface)"
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing { Result Function (); }
public abstract class King : IKing
{
public abstract Result Function ();
}
public class KingA : King
{
public override Result Function () => new ResultA ();
}
public class KingB : King
{
public override Result Function () => new ResultB ();
{
return new ResultB ();
}
}
"no interface"
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public abstract class King
{
public abstract Result Function ();
}
public class KingA : King
{
public override Result Function () => new ResultA ();
}
public class KingB : King
{
public override Result Function () => new ResultB ();
}
使用协方差
参见 .net fiddler here. Read more about Covariance and Contravariance
public abstract class Result { }
public class ResultA : Result { }
public class ResultB : Result { }
public interface IKing<out T> where T : Result {}
public abstract class King<T> : IKing<T> where T : Result
{
public abstract T Get();
}
public class KingA : King<ResultA>
{
public override ResultA Get()
{
return new ResultA();
}
}
public class KingB : King<ResultB>
{
public override ResultB Get()
{
return new ResultB();
}
}
public class TestClass
{
King<ResultA> a = new KingA(); // allowed by public static implicit operator King<Result>(KingA v)
King<ResultB> b = new KingB(); // allowed by public static implicit operator King<Result>(KingB v)
KingA ka = new KingA();
List<IKing<Result>> lista = new List<IKing<Result>>();
public void Test()
{
lista.Add(ka);
}
}