通导特性的方法在C#(Pass Property to the Method in C#)

2019-09-16 15:06发布

我需要通过一些类型(每次一个类型)的属性选择,假设这是我喜欢的类型:

public class Product {

    [PrimaryKey]
    public long Id { get; set; }
    [DisplayName("Name")]
    public string Title { get; set; }
    [Foreignkey(Schema = "Products", Table = "MajorCategory", Column = "Id")]
    [DisplayName("MCat")]
    public string MajorCategory { get; set; }
    [Foreignkey(Schema = "Products", Table = "Category", Column = "Id")]
    [DisplayName("Cat")]
    public string Category { get; set; }
    public long CategoryId { get; set; }
    [BoolAsRadio()]
    public bool IsScanAllowed { get; set; }
}

所以,我需要一种方法来传递这种类型的其他类型(目标类型)的属性列表,并使用属性名称和属性,而我不需要值,类似下面的伪代码:

List<Property> propertyList = new List<Property>();
propertyList.Add(Product.Id);
PropertyList.Add(Product.Title);
TargetType target = new TargetType();
target.Properties = propertyList;


public class TargetType  {

   public List<Property> Properties { get; set;}

   GetAttributes() {

      foreach(Property item in Properties){

         Console.WriteLine(item.Name)

         //Get Attributes
      }
   }


}

有没有什么办法来传递就像Product.Id和使用名称和该属性? 我不知道,但也许PropertyInfo可以帮助,我想正好可以通过对象的名单,但在这种情况下,我不能使用属性和名称,你有什么建议来处理呢? 或这样的事情? 如果我错了,在一切让我怎么能实现呢?

Answer 1:

好笑的是,我只是回答了类似的问题,或者至少我觉得是。

它看起来像你想两种类型的属性连接成一个? 你需要一个ExpandoObject:

http://msdn.microsoft.com/en-us/library/system.dynamic.expandoobject%28v=vs.100%29.aspx

对于嵌套合并的实现,看到这一点:

C#深/嵌套/递归动态/ Expando的对象合并

基本上,你想要的属性的键列表,从启动。 下面的代码会做任何.NET对象:

var props = object.GetType().GetProperties().ToDictionary<PropertyInfo, string>(prop => prop.Name);

之后,它取决于什么恰恰是你想要实现 - 对象的真实副本,与另一个合并,或者只是保持列表。



Answer 2:

您可以使用反射在.NET这里:

List<PropertyInfo> propertyList = new List<PropertyInfo>();
Type productType = typeof (Product);

propertyList.Add(productType.GetProperty("Id"));
propertyList.Add(productType.GetProperty("Title"));
TargetType target = new TargetType();
target.Properties = propertyList;

public class TargetType  {

   public List<PropertyInfo> Properties { get; set;}

   List<object> GetAttributes()
   {
       List<object> attributes = new List<object>();

       foreach(PropertyInfo item in Properties)
       {
           Console.WriteLine(item.Name);
           attributes.AddRange(item.GetCustomAttributes(true));
       }

       return attributes;
   }
}


Answer 3:

你可以用列表PropertyInfoList<PropertyInfo>为你的类型TargetType .Properties 。 要获得的属性,你可以尝试一下这样的使用Reflection

targetType.Properties = product.GetType().GetProperties().ToList();


Answer 4:

您可使用表达式树的属性列表,例如,你可以做这样的事情:


var propertiesListBuilder = new PropertiesListBuilder<Product>();
propertiesListBuilder
    .AddProperty(_ => _.Id)
    .AddProperty(_ => _.Title);

var target = new TargetType();
target.Properties = propertiesListBuilder.Properties;

这里唯一关心的是性能,即它可能是一遍又一遍重现这样的属性列表不是好主意,最有可能,他们应该被缓存。 同时你会得到智能感知,编译器检查和重构支持你的财产清单。

下面是这东西的样本实施。


static class PropertyInfoProvider<T>
{
    public static PropertyInfo GetPropertyInfo<TProperty>(Expression<Func<T, TProperty>> expression)
    {
        var memberExpression = (MemberExpression)expression.Body;

        return (PropertyInfo)memberExpression.Member;
    }
}

class PropertiesListBuilder<T>
{
    public IEnumerable<PropertyInfo> Properties
    {
        get
        {
            return this.properties;
        }
    }

    public PropertiesListBuilder<T> AddProperty<TProperty>(
        Expression<Func<T, TProperty>> expression)
    {
        var info = PropertyInfoProvider<T>.GetPropertyInfo(expression);
        this.properties.Add(info);

        return this;
    }

    private List<PropertyInfo> properties = new List<PropertyInfo>();
}



Answer 5:

typeof(Product).GetProperties()会给你所有的(公共)属性PropertyInfo[]

另请参见MSDN 。



文章来源: Pass Property to the Method in C#