从 IEnumerable 获取类型 T;
有没有办法通过反射从 IEnumerable
检索类型 T
?
例如
我有一个变量 IEnumerable
info;我想通过反射检索 Child 的类型
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(13)
因此,
打印
System.String
。请参阅 MSDN 了解
Type.GetGenericArguments.
编辑:我相信这将解决评论中的问题:
某些对象实现多个通用
IEnumerable
,因此有必要返回它们的枚举。编辑:尽管如此,我不得不说,对于一个类来说,为多个
T
实现IEnumerable
是一个糟糕的主意。Thusly,
prints
System.String
.See MSDN for
Type.GetGenericArguments
.Edit: I believe this will address the concerns in the comments:
Some objects implement more than one generic
IEnumerable
so it is necessary to return an enumeration of them.Edit: Although, I have to say, it's a terrible idea for a class to implement
IEnumerable<T>
for more than oneT
.我只是做一个扩展方法。这与我投入的一切都有效。
I'd just make an extension method. This worked with everything I threw at it.
我有类似的问题。所选答案适用于实际情况。
就我而言,我只有一个类型(来自
PropertyInfo
)。当类型本身是
typeof(IEnumerable)
而不是IEnumerable
的实现时,所选答案将失败。对于这种情况,可以进行以下操作:
I had a similar problem. The selected answer works for actual instances.
In my case I had only a type (from a
PropertyInfo
).The selected answer fails when the type itself is
typeof(IEnumerable<T>)
not an implementation ofIEnumerable<T>
.For this case the following works:
如果您知道
IEnumerable
(通过泛型),那么只需typeof(T)
就可以了。否则(对于object
或非泛型IEnumerable
),检查实现的接口:If you know the
IEnumerable<T>
(via generics), then justtypeof(T)
should work. Otherwise (forobject
, or the non-genericIEnumerable
), check the interfaces implemented:非常感谢您的讨论。我用它作为下面解决方案的基础,它适用于我感兴趣的所有情况(IEnumerable、派生类等)。我想我应该在这里分享,以防有人也需要它:
Thank you very much for the discussion. I used it as a basis for the solution below, which works well for all cases that are of interest to me (IEnumerable, derived classes, etc). Thought I should share here in case anyone needs it also:
我知道这有点老了,但我相信这种方法将涵盖评论中指出的所有问题和挑战。感谢 Eli Algranti 对我工作的启发。
I know this is a bit old, but I believe this method will cover all the problems and challenges stated in the comments. Credit to Eli Algranti for inspiring my work.
这是一个递归函数,它将首先深入泛型类型列表,直到获得没有内部泛型类型的具体类型定义。
我用这种类型测试了这个方法:
ICollection>>>
应该返回
T
This is a recursive function that will go depth first down the list of generic types until it gets a concrete type definition with no inner generic types.
I tested this method with this type:
ICollection<IEnumerable<ICollection<ICollection<IEnumerable<IList<ICollection<IEnumerable<T>>>>>>>>
which should return
T
只需使用
typeof(T)
编辑:
或者,如果您没有 T,请在实例化对象上使用 .GetType().GetGenericParameter()。
Just use
typeof(T)
EDIT:
Or use .GetType().GetGenericParameter() on an instantiated object if you don't have T.
对于更简单的情况,它是
IEnumerable
或T
的替代方案 - 请注意使用GenericTypeArguments
而不是GetGenericArguments ()
。An alternative for simpler situations where it's either going to be an
IEnumerable<T>
orT
- note use ofGenericTypeArguments
instead ofGetGenericArguments()
.这是对 Eli Algranti 解决方案的改进,因为它也适用于
IEnumerable
类型位于继承树中任何级别的情况。此解决方案将从任何
Type
获取元素类型。如果类型不是IEnumerable
,它将返回传入的类型。对于对象,请使用GetType
。对于类型,请使用typeof
,然后对结果调用此扩展方法。This is an improvement on Eli Algranti's solution in that it will also work where the
IEnumerable<>
type is at any level in the inheritance tree.This solution will obtain the element type from any
Type
. If the type is not anIEnumerable<>
, it will return the type passed in. For objects, useGetType
. For types, usetypeof
, then call this extension method on the result.typeof(IEnumerable)
。GetGenericArguments()
[0]
将返回第一个泛型参数 - 在本例中为typeof(Foo)
。typeof(IEnumerable<Foo>)
.GetGenericArguments()
[0]
will return the first generic argument - in this casetypeof(Foo)
.这就是我通常这样做的方式(通过扩展方法):
this is how I usually do it (via extension method):
这是我不可读的 Linq 查询表达式版本。
请注意,该方法还考虑了非泛型 IEnumerable,在这种情况下它返回 object,因为它需要 Type 而不是一个具体的实例作为参数。顺便说一下,对于x代表未知,我发现这个视频很有趣,尽管它无关紧要..
Here's my unreadable Linq query expression version ..
Note the method also takes non-generic
IEnumerable
into account, it returnsobject
in this case, because it takes aType
rather than a concrete instance as the argument. By the way, for x represents the unknown, I found this video insteresting, though it is irrelevant ..