这令人困惑,因为我看似矛盾的错误.
我使用的是仿制药,限制T到Something,然后制约U到AnOperation<Something>.
我预计一个对象AnOperation<Something>从现在开始被认为是类型U.但是,我收到了错误:
Cannot implicitly convert type 'ConsoleApp1.AnOperation<T>' to 'U'
那真是怪了.好吧,我试着明确地将它投射到U,然后我收到了这个错误:
Cannot convert type 'ConsoleApp1.AnOperation<T>' to 'U' 其中也说明了 Cast is redundant
namespace ConsoleApp1
{
class Program
{
static void Main(string[] args)
{
}
}
class MyClass<T, U>
where T : Something
where U : AnOperation<Something>
{
public U GetAnOperationOfSomething()
{
AnOperation<T> anOperation = new AnOperation<T>();
return anOperation; // Cannot implicitly convert type 'ConsoleApp1.AnOperation<T>' to 'U'
// return (U)anOperation; // Cannot convert type 'ConsoleApp1.AnOperation<T>' to 'U' also Cast is redundant
}
}
public class Something
{
}
public class AnOperation<T>
where T : Something
{
}
}
Run Code Online (Sandbox Code Playgroud)
这里发生了什么事?
编辑:我试图了解语言级别的问题,而不是寻找实际问题的解决方法.
Sef*_*efe 11
你的约束几乎让你正确,但并不完全.你定义
where U : AnOperation<Something>
Run Code Online (Sandbox Code Playgroud)
但是你创造了
AnOperation<T> anOperation = new AnOperation<T>()
Run Code Online (Sandbox Code Playgroud)
那不是一回事.如果您将约束更改为...
where U : AnOperation<T>
Run Code Online (Sandbox Code Playgroud)
...你会好起来的.
另一个问题是,虽然每一个U都是一个AnOperation<T>,但不是每个AnOperation<T>都是一个U.当你宣布......
public U GetAnOperationOfSomething()
Run Code Online (Sandbox Code Playgroud)
...你正在保证方法返回的是一个U.AnOperation<T>不能满足那种保证.
你是用类型转换来解决这个问题的U.这违反了泛型类的目的,因为每个U必须是AnOperation<T>或者您将获得运行时异常.这使得整个类型参数变得U不必要.你真正想做的是创造一个U.您可以使用new()约束:
class MyClass<T, U>
where T : Something
where U : AnOperation<T>, new()
{
public U GetAnOperationOfSomething()
{
U anOperation = new U();
//...
return anOperation;
}
}
Run Code Online (Sandbox Code Playgroud)
该new()约束保证U将有一个公共的默认构造函数,它可以调用.
T在你的类中是继承自的任何类Something.
U是继承自的任何类AnOperation<Something>.假设您有这样的子类:
public class ChildOperation<T> : AnOperation<T> {}
Run Code Online (Sandbox Code Playgroud)
现在你U可能是ChildOperation<Something>,并且你不能返回父类(AnOperation<T>)的实例作为子类的实例(U这是ChildOperation<Something>).它T确实可能出错ChildSomething,因为AnOperation<Something>无法隐式转换为AnOperation<ChildSomething>.长话短说 - AnOperation<T>确实不能总是转换为你的U类型,所以编译是正确的.
| 归档时间: |
|
| 查看次数: |
976 次 |
| 最近记录: |