2010-09-28 63 views
5

我的问题是否有任何方法来检索参数列表及其值使用反射?使用反射获取参数的参数

我想使用反射从PropertyInfo中获取参数列表。

Author author = (Author)attribute; 
string name = author.name; 

是不行的。因为会有很多属性,这不是typeof Author。

[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property, AllowMultiple = true)] 
public class Author : Attribute 
{ 
    public Author(string name, int v) 
    { 
     this.name = name; 
     version = v; 
    } 

    public double version; 
    public string name; 
} 

public class TestClass 
{ 
    [Author("Bill Gates", 2)] 
    public TextBox TestPropertyTextBox { get; set; } 
} 

回答

0

我假设通过参数列表,你的意思是所有属性使用的列表?

如果不是,这段代码将告诉你如何在整个类中使用反射来获取属性。但你应该能够接受你需要的东西。

因此,这里是内部TestClass

public IEnumberable<Result> GetAttributesFromClass(TestClass t) 
{ 

    foreach(var property in t.GetType().GetProperties()) 
    { 
     foreach(Author author in property.GetCustomAttributes(typeof(Arthor), true)) 
     { 
      // now you have an author, do what you please 
      var version = author.version; 
      var authorName = author.name; 

      // You also have the property name 
      var name = property.Name; 

      // So with this information you can make a custom class Result, 
      // which could contain any information from author, 
      // or even the attribute itself 
      yield return new Result(name,....); 
     } 

    } 
} 

找到某种类型的所有属性的方法,对任何属性然后你可以去:

var testClass = new TestClass(); 

var results = GetAttributesFromClass(testClass); 

此外,您可能需要您public double versionstring name属性。 事情是这样的:

public double version 
{ 
    get; 
    private set; 
} 

,这将使version从构造函数中设置,并从任何地方读取。

+0

谢谢。我的情况是,不要使用静态类。所以使用Author author =(Author)属性;不好。我想使用反射从PropertyInfo获取参数列表。 – seasong 2010-09-28 03:16:12

+0

你可以定义参数列表吗? – PostMan 2010-09-28 03:18:41

+0

参数列表是我可以获得(“比尔盖茨”,2)动态使用反射与必须使用“作者”投射属性。因为会有很多这样的Attribute,有些可能不是Author的属性。 – seasong 2010-09-28 03:25:37

4

使用该程序

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Windows.Forms; 

namespace ConsoleApplication1 { 
    class Program { 
     static void Main(string[] args) { 
      Console.WriteLine("Reflecting TestClass"); 
      foreach (var property in typeof(TestClass).GetProperties()) { 
       foreach (Author author in property.GetCustomAttributes(typeof(Author), true).Cast<Author>()) { 
        Console.WriteLine("\tProperty {0} Has Author Attribute Version:{1}", property.Name, author.version); 
       } 
      } 
      var temp = new TestClass(); 
      Console.WriteLine("Reflecting instance of Test class "); 
      foreach (var property in temp.GetType().GetProperties()) { 
       foreach (Author author in property.GetCustomAttributes(typeof(Author), true).Cast<Author>()) { 
        Console.WriteLine("\tProperty {0} Has Author Attribute Version:{1}", property.Name, author.version); 
       } 
      } 
     } 

    } 

    [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property, AllowMultiple = true)] 
    public class Author : Attribute { 
     public Author(string name, int v) { 
      this.name = name; 
      version = v; 
     } 

     public double version; 
     string name; 
    } 

    public class TestClass { 
     [Author("Bill Gates", 2)] 
     public TextBox TestPropertyTextBox { get; set; } 
    } 

} 

我得到这样的输出:

alt text

0
string name = author.name; 

是不允许的,因为外地name是不公开的。如果你让name公开,它会起作用吗?

+0

对不起,这是一个错字,我把公众加回来了。 – seasong 2010-09-28 03:28:10

+0

您的最新编辑揭示了您的问题。使用带有类型参数的'GetCustomAttributes'来过滤并且只查看'Author'的属性,或者使用'Author author = attribute作为Author;'而不是一个强制类型来执行动态类型检查,而忽略那些返回'null'。 – 2010-09-28 04:53:04

0

我在我的一个应用程序中遇到同样的问题。这是我的解决方案:

public static string GetAttributesData(MemberInfo member) 
{    
    StringBuilder sb = new StringBuilder(); 
    // retrives details from all attributes of member 
    var attr = member.GetCustomAttributesData(); 
    foreach (var a in attr) 
    { 
     sb.AppendFormat("Attribute Name  : {0}", a) 
      .AppendLine(); 
     sb.AppendFormat("Constructor arguments : {0}", string.Join(", ", a.ConstructorArguments)) 
      .AppendLine(); 
     if (a.NamedArguments != null && a.NamedArguments.Count > 0) 
     sb.AppendFormat("Named arguments  : {0}", string.Join(", ", a.NamedArguments)) 
      .AppendLine(); 
     sb.AppendLine(); 
    }    
    return sb.ToString(); 
} 

我测试了你的例子。

var t = typeof (TestClass); 
var prop = t.GetProperty("TestPropertyTextBox", BindingFlags.Public | BindingFlags.Instance); 
var scan = Generator.GetAttributesData(prop); 

这里是输出:

Attribute Name  : [Author("Bill Gates", (Int32)2)] 
Constructor arguments : "Bill Gates", (Int32)2