【问题标题】:Looping through Class Variables using reflection使用反射循环遍历类变量
【发布时间】:2018-08-05 16:34:30
【问题描述】:

我想遍历一个类并列出它的变量。 这已在 SO 上被多次询问,我已经尝试了所有答案。

由于某种原因,我无法让解决方案发挥作用。 当我运行下面的代码时(应该循环遍历类两次,只是为了尝试不同的方式),答案只是显示为“Test1”,这意味着它没有遍历类。

有谁知道为什么循环没有运行?

public partial class Tables : Form
{
  private void dataGridViewNodes_CellValueChanged(object sender, DataGridViewCellEventArgs e)
    {
        Debug.WriteLine("test1");
        //Simple Test
        foreach (PropertyInfo prop in typeof(NodeHeaders).GetProperties())
        {
            Debug.WriteLine("test2");
            Debug.WriteLine(prop.Name);
        }

        //the above should have looped through the class so let's try again
        var nodeHeaders = new NodeHeaders();
        Type t = nodeHeaders.GetType();
        string fieldName;
        object propertyValue;

        // Use each property of the object passed in
        foreach (PropertyInfo pi in t.GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic))
        {
            // Get the name of the property
            fieldName = pi.Name;

            // Get the value of the property
            propertyValue = pi.GetValue(nodeHeaders, null);
            Debug.WriteLine("test3");
            Debug.WriteLine(fieldName + ": " + (propertyValue == null ? "null" : propertyValue.ToString()));
        }

    }
}

public class NodeHeaders
{
    public static string node_name = "Conduit Name";
    public static string x = "Easting (m)";
    public static string y = "Northing (m)";
    public static string z_cover = "Cover Level (m)";

}

编辑:

根据 Nico Schertler 的评论表单解释说我需要循环遍历字段而不是属性,我还尝试了以下相同的结果。

Type type = typeof(NodeHeaders);
foreach (var p in type.GetFields(System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.NonPublic))
{
    var v = p.GetValue(null); // static classes cannot be instanced, so use null...
    Debug.WriteLine(v.ToString());
}

【问题讨论】:

  • NodeHeaders 没有任何属性。那些是领域。另外,指定BindingFlags.Static
  • @Nico Schertler 感谢您的回复。我已经按照你的建议用一个例子更新了这个问题,但我得到了相同的结果。我确定我错过了一些愚蠢的东西。
  • 指定BindingFlags.Public 查找公共成员。
  • @Nico Schertler,太好了,这成功了。感谢您的帮助。

标签: c# loops class reflection


【解决方案1】:

由于您要访问的是公共静态字段,因此您应该使用 t.GetFields(BindingFlags.Static | BindingFlags.Public)

foreach (var field in typeof(NodeHeaders).GetFields(BindingFlags.Static | BindingFlags.Public))
{        
    // Get the name of the property
    string fieldName = field.Name;
    // Get the value of the property
    object propertyValue = field.GetValue(null);
    Console.WriteLine("test3");
    Console.WriteLine(fieldName + ": " + (propertyValue == null ? "null" : propertyValue.ToString()));
}

这将正确访问字段值:

【讨论】:

    【解决方案2】:

    这对你有用吗?

    public class NodeHeaders
    {
        public static string node_name = "Conduit Name";
        public static string x = "Easting (m)";
        public static string y = "Northing (m)";
        public static string z_cover = "Cover Level (m)";
    
    }
    
    class Program
    {
    
    
    
    
        static void Main(string[] args)
        {
    
            DataGridViewNodes_CellValueChanged();
    
    
    
        }
    
    private static void DataGridViewNodes_CellValueChanged()
    {
            try
            {
    
    
        foreach (FieldInfo prop in typeof(NodeHeaders).GetFields())
        {
    
            object item = prop.GetValue(null);
                    Console.WriteLine($"{prop.Name} = {item.ToString()}");
        }
    
            }
            catch (Exception ex)
            {
    
                throw;
            }
    
            Console.ReadKey();
    
    }
    

    }

    【讨论】:

      猜你喜欢
      • 2018-10-19
      • 1970-01-01
      • 2012-11-09
      • 1970-01-01
      • 2019-01-07
      • 2015-06-09
      • 2014-10-25
      • 1970-01-01
      • 2020-08-18
      相关资源
      最近更新 更多