简体   繁体   English

如何确定Type是一个自定义结构?

[英]How to decide a Type is a custom struct?

For a Type , there is a property IsClass in C#, but how to decide a Type is a struct? 对于Type ,C#中有一个属性IsClass ,但如何判断Type是一个struct?

Although IsValueType is a necessary condition, it is obviously not enough. 虽然IsValueType是必要条件,但显然还不够。 For an int is a value type also. 对于int也是值类型。

Someone suggests the following code: 有人建议使用以下代码:

bool IsStruct = type.IsValueType && !type.IsEnum && !type.IsPrimitive;

But I am not sure whether it is an accurate method. 但我不确定这是否是一种准确的方法。 The formula should tell the difference between struct and other types such as DateTime , int and array s. 公式应该告诉struct和其他类型之间的区别,比如DateTimeintarray s。

As some friends have pointed out that here, I mean user defined struct and not predefined types , such as DateTime . 正如一些朋友指出的那样,我指的是用户定义的结构而不是预定义的类型 ,例如DateTime

Technically, an int is also a struct. 从技术上讲,int也是一个结构。 IsPrimitive just checks if the type is one of the primitive types the CLR handles a little differently. IsPrimitive只是检查类型是否是CLR处理的原始类型之一。 You should be fine with the suggestion IsValueType && !IsEnum && !IsPrimitive . 建议IsValueType && !IsEnum && !IsPrimitive你应该IsValueType && !IsEnum && !IsPrimitive

If you want only custom structs (ie those not supplied by the BCL), you may have luck excluding types with a FullName that starts with "System." 如果您只想要自定义结构(即那些不是由BCL提供的结构),您可以幸运地排除具有以"System."开头的FullName的类型"System." , or only including the ones you're interested in by filtering by assembly or namespace, or use a custom attribute. ,或仅通过按装配或命名空间过滤包含您感兴趣的那些,或使用自定义属性。

Should be at least 至少应该是

bool isStruct = type.IsValueType && !type.IsEnum &&
               !type.IsPrimitive && type != typeof(decimal);

http://msdn.microsoft.com/en-us/library/bfft1t3c.aspx says: IsValueType is true if Type is in {bool, byte, char, decimal, double, enum, float, int, long, sbyte, short, struct, uint, ulong, ushort}. http://msdn.microsoft.com/en-us/library/bfft1t3c.aspx说:如果Type在{bool,byte,char,decimal,double,enum,float,int,long,sbyte,short中,则IsValueType为true ,struct,uint,ulong,ushort}。

http://msdn.microsoft.com/en-us/library/system.type.isprimitive%28v=vs.110%29.aspx says: IsPrimitive is true if Type is in {Boolean, Byte, SByte, Int16, UInt16, Int32, UInt32, Int64, UInt64, IntPtr, UIntPtr, Char, Double, and Single}. http://msdn.microsoft.com/en-us/library/system.type.isprimitive%28v=vs.110%29.aspx说:如果Type在{Boolean,Byte,SByte,Int16,UInt16中,则IsPrimitive为真,Int32,UInt32,Int64,UInt64,IntPtr,UIntPtr,Char,Double和Single}。

Than for IsStruct you can use method like this: 对于IsStruct,你可以使用这样的方法:

public static bool IsStruct(this Type type)
{
    return type.IsValueType 
            && !type.IsPrimitive 
            && !type.IsEnum 
            && type != typeof(decimal);
}

You're going to have a tough time with this. 你将会遇到困难。 The base Framework doesn't know what all the predefined types in other parts of the Framework are. 基础框架不知道框架其他部分中的所有预定义类型是什么。 It's unreasonable to expect the core Framework to know about System.Drawing.Point , for example. 例如,期望核心框架了解System.Drawing.Point是不合理的。

OregonGhost has probably the best answer : get the type info and check the FullName property to see if it starts with "System." OregonGhost可能是最好的答案 :获取类型信息并检查FullName属性以查看它是否以"System."开头"System." . But you'll also need to check for "Microsoft." 但是你还需要检查"Microsoft." and "FSharp" , and possibly others. "FSharp" ,可能还有其他人。 Just click on "Add a reference" in Visual Studio, and see what names come up. 只需在Visual Studio中单击“添加引用”,然后查看出现的名称。

And then you might risk blocking too much. 然后你可能会冒很大的阻塞风险。 Microsoft distributes some assemblies via NuGet packages, and the types in those assemblies often have names that start with "System." Microsoft通过NuGet包分发一些程序集,这些程序集中的类型通常具有以"System."开头的名称"System." or "Microsoft." "Microsoft." Do you consider those "Built in" types even though they're not distributed with the Framework? 您是否考虑过那些“内置”类型,即使它们没有随框架一起分发?

它对我有用!x.PropertyType.IsSecurityTransparent && x.PropertyType.IsClass

Not a perfect solution, but you can always consider narrowing the search by known types within the assemblies you wish to search: 不是一个完美的解决方案,但您始终可以考虑在要搜索的程序集中按已知类型缩小搜索范围:

System.Reflection.Assembly.GetAssembly(tyepof(OneOfMyTypes))
    .GetExportedTypes()
    .Where(t => t.IsValueType);

The helps eliminate false positives (safer?), but it's less portable. 有助于消除误报(更安全吗?),但它不那么便携。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM