[英]c# implicit conversion from base class
I have a collection class like this: 我有一个这样的集合类:
public class SomeDataCollection : List<ISomeData>
{
// some method ...
}
but I can't do this: 但我不能这样做:
SomeDataCollection someDatas = new List<ISomeData>();
Cannot implicitly convert type
List<ISomeData>
toSomeDataCollection
.无法将类型
List<ISomeData>
隐式转换为SomeDataCollection
。 An explicit conversion exists (are you missing a cast?)存在显式转换(您是否错过了演员?)
so I try to create an implicit coverter inside SomeDataCollection
collection class: 所以我尝试在
SomeDataCollection
集合类中创建一个隐式转换器:
public static implicit operator SomeDataCollection(List<ISomeData> l)
{
var someDatas = new SomeDataCollection();
someDatas.AddRange(l);
return someDatas;
}
but it said that I can't create such converter: 但它说我不能创建这样的转换器:
SomeDataCollection.implicit operator SomeDataCollection(List<ISomeData>)
: user-defined conversions to or from a base class are not allowedSomeDataCollection.implicit operator SomeDataCollection(List<ISomeData>)
: 不允许在基类之间进行用户定义的转换
And when I cast it like this: 当我这样投出时:
SomeDataCollection someDatas = (SomeDataCollection)new List<ISomeData>();
it throws an error that said: 它抛出一个错误,说:
System.InvalidCastException: Unable to cast object of type
List<ISomeData>
to typeSomeDataCollection
.System.InvalidCastException:无法转换
List<ISomeData>
类型的对象以键入SomeDataCollection
。
How can I do this: 我怎样才能做到这一点:
SomeDataCollection someDatas = new List<ISomeData>();
without getting an error? 没有收到错误? Please help.
请帮忙。 Thanks in advance.
提前致谢。
A new List<ISomeData>();
一个
new List<ISomeData>();
is still just a List<ISomeData>
. 仍然只是一个
List<ISomeData>
。 It isn't a SomeDataCollection
. 它不是
SomeDataCollection
。 The point of subclassing is that the subclass could have extra state etc, but an object (once created) never changes type. 子类化的要点是子类可以有额外的状态等,但是一个对象(一旦创建) 永远不会改变类型。
You are not allowed to create operators between types in the same hierarchy, as that would subvert the usual and expected casting behaviour. 不允许在同一层次结构中的类型之间创建运算符,因为这会破坏通常和预期的转换行为。
You could use simply: 您可以简单地使用:
var data = new SomeDataCollection();
However I should add that frankly it is rarely useful to subclass List<T>
. 但是我应该坦率地补充一下,对
List<T>
进行子类化很少有用。 Not least, it doesn't expose any useful virtual
methods, so you can't tweak the behaviour. 尤其是,它不会暴露任何有用的
virtual
方法,因此您无法调整行为。 I would honestly just use a List<ISomeData>
(and remove SomeDataCollection
completely) unless I have a clear and demonstrable purpose for it. 老实说,我只是使用
List<ISomeData>
(并完全删除SomeDataCollection
),除非我有明确和可证明的目的。 And then: I might either encapsulate the list, or inherit from Collection<T>
. 然后:我可以封装列表,也可以从
Collection<T>
继承。
You could always just add the method as an extension method? 您可以随时将该方法添加为扩展方法吗?
public static class Utils {
public static void SomeMethod(this IList<ISomeData> list) {
...
}
}
then: 然后:
var list = new List<ISomeData>();
...
list.SomeMethod();
First of all, why do you want to write new List<ISomeData>
into a variable defined as SomeDataCollection
? 首先,为什么要将
new List<ISomeData>
写入定义为SomeDataCollection
的变量? It is possible that you actually wanted to SomeDataCollection someDatas = new SomeDataCollection();
你有可能真的想要
SomeDataCollection someDatas = new SomeDataCollection();
As for error messages, the first error message tells you that List<ISomeData>
is not derived from SomeDataCollection
, therefore you can't do with it something you would do with SomeDataCollection
, therefore you can't write it to the variable which is defined as SomeDataCollection
(imagine eg if SomeDataCollection
had public void someMethod()
in it, and later in the code you'd call someDatas.someMethod()
). 对于错误消息,第一条错误消息告诉您
List<ISomeData>
不是从SomeDataCollection
派生的,因此您无法使用SomeDataCollection
执行SomeDataCollection
,因此您无法将其写入已定义的变量作为SomeDataCollection
(想象一下,如果SomeDataCollection
在其中有public void someMethod()
,稍后在代码中你将调用someDatas.someMethod()
)。
The second error message tells you that converters are intended for converting between completely different types, not between the based and derived type. 第二条错误消息告诉您转换器用于在完全不同的类型之间进行转换,而不是在基于类型和派生类型之间进行转换。 Otherwise, what would you expect to get eg in the following example:
否则,您希望获得什么,例如在以下示例中:
SomeDataCollection a = new SomeDataCollection();
List<ISomeData> b = (List<ISomeData>)a;
SomeDataCollection c = (SomeDataCollection)b;
Should it call your converter or not? 它应该叫你的转换器吗?
Basically code you're trying to write is very wrong to begin for, so we need to know what're you trying to do, and then maybe well'be able to tell you the solution of your root problem (and not of the problem "how to make this code compile"). 基本上你要编写的代码是非常错误的,所以我们需要知道你想要做什么,然后很可能能够告诉你你的根问题的解决方案(而不是问题的解决方案) “如何编译此代码”)。
Isn't it better to implement a constructor in SomeDataCollection
? 在
SomeDataCollection
实现构造函数不是更好吗?
public SomeDataCollection() : base() { }
This could of course be complemented with 这当然可以补充
public SomeDataCollection(IEnumerable<ISomeData> collection)
: base(collection) { }
Then you should be able to initialize your SomeDataCollection
like this instead: 然后你应该能够像这样初始化你的
SomeDataCollection
:
SomeDataCollection someData = new SomeDataCollection();
SomeDataCollection someOtherData =
new SomeDataCollection(collectionOfSomeData);
and still have access to all the public methods and properties in List<ISomeData>
. 并且仍然可以访问
List<ISomeData>
所有公共方法和属性。
It does not problem with generics. 它与泛型没有问题。 In C# you are not allowed to explicitely convert a base class into a derived class.
在C#中,不允许将基类明确地转换为派生类。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.