我正在尝试使用 MetadataType 属性类将属性应用于字段。我无法将自定义属性应用于分部类中的字段。我一直关注的一些例子是 here和 here .
我的最终目标是尝试标记类中需要我“做一些工作”的所有字段。
在下面的示例中,我希望字段“Name”应用 FooAttribute。在现实生活中,我正在处理生成的代码......
在我非常人为的示例中,我有一个部分类 - Cow,它是生成的代码;
namespace Models
{
public partial class Cow
{
public string Name;
public string Colour;
}
}
我需要 Name 字段来使用我的 FooAttribute,所以我已经这样做了;
using System;
using System.ComponentModel.DataAnnotations;
namespace Models
{
public class FooAttribute : Attribute { }
public class CowMetaData
{
[Foo]
public string Name;
}
[MetadataType(typeof(CowMetaData))]
public partial class Cow
{
[Foo]
public int Weight;
public string NoAttributeHere;
}
}
这对于应用了 FooAttribute 的 Weight 字段非常有效 - 但我希望如此,因为它位于分部类中。名称字段不会从元数据中获取属性,而这正是我真正需要的。
我错过了什么,还是我搞错了?
更新:这就是我使用 FooAttribute 搜索字段的方式;
public static void ShowAllFieldsWithFooAttribute(Cow cow)
{
var myFields = cow.GetType().GetFields().ToList();
foreach (var f in myFields)
{
if (Attribute.IsDefined(f, typeof(FooAttribute)))
{
Console.WriteLine("{0}", f.Name);
}
}
}
结果是:
重量
但我期待:
姓名
重量
最佳答案
属性是元数据的一部分,它们不会影响编译结果。为类设置 MetadataType
属性不会将所有元数据传播到类的属性/字段。因此,您必须读取代码中的 MetadataType
属性,并使用 MetadataType
属性中定义的类型的元数据,而不是初始类(或在您的情况下一起使用)
检查示例:
var fooFields = new Dictionary<FieldInfo, FooAttribute>();
var cowType = typeof (Cow);
var metadataType = cowType.GetCustomAttribute<MetadataTypeAttribute>();
var metaFields = metadataType?.MetadataClassType.GetFields() ?? new FieldInfo[0];
foreach (var fieldInfo in cowType.GetFields())
{
var metaField = metaFields.FirstOrDefault(f => f.Name == fieldInfo.Name);
var foo = metaField?.GetCustomAttribute<FooAttribute>()
?? fieldInfo.GetCustomAttribute<FooAttribute>();
if (foo != null)
{
fooFields[fieldInfo] = foo;
}
}
关于C# 自定义属性未应用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47425155/