【问题标题】:Retrieve only static fields declared in Java class仅检索在 Java 类中声明的静态字段
【发布时间】:2011-03-26 05:49:57
【问题描述】:

我有以下课程:

public class Test {
    public static int a = 0;
    public int b = 1;
}

是否可以使用反射来仅获取静态字段的列表?我知道我可以使用Test.class.getDeclaredFields() 获得所有字段的数组。但似乎无法确定 Field 实例是否代表静态字段。

【问题讨论】:

标签: java reflection static field


【解决方案1】:

你可以这样做:

Field[] declaredFields = Test.class.getDeclaredFields();
List<Field> staticFields = new ArrayList<Field>();
for (Field field : declaredFields) {
    if (java.lang.reflect.Modifier.isStatic(field.getModifiers())) {
        staticFields.add(field);
    }
}

【讨论】:

    【解决方案2】:

    如果您可以将开源依赖项添加到您的项目中,您也可以使用 FieldUtils.readDeclaredStaticField(Test.class,"a")

    【讨论】:

    • 这并没有给出静态字段的列表。
    【解决方案3】:

    这很简单,你可以使用修饰符来检查一个字段是否是静态的。 这是此类任务的示例代码。

    public static void printModifiers(Object o) {
        Class c = o.getClass();
        int m = c.getModifiers();
        if (Modifier.isPublic(m))
            System.out.println ("public");
        if (Modifier.isAbstract(m))
            System.out.println ("abstract");
        if (Modifier.isFinal(m))
            System.out.println ("final");
        if(Modifier.isStatic(m))
            System.out.println("static");
    }
    

    【讨论】:

      【解决方案4】:

      我偶然发现了这个问题,觉得它需要使用流更新 Java 8:

      public static List<Field> getStatics(Class<?> clazz) {
          List<Field> result;
      
          result = Arrays.stream(clazz.getDeclaredFields())
                  // filter out the non-static fields
                  .filter(f -> Modifier.isStatic(f.getModifiers()))
                  // collect to list
                  .collect(toList());
      
          return result;
      }
      

      显然,为了便于阅读,该示例进行了一些修饰。实际上,您可能会这样写:

      public static List<Field> getStatics(Class<?> clazz) {
          return Arrays.stream(clazz.getDeclaredFields()).filter(f ->
              Modifier.isStatic(f.getModifiers())).collect(toList());
      }
      

      【讨论】:

      • “实际上,您可能会这样写”......为什么您认为“实际上”可读性并不重要?
      • 首先,我认为在这样的网站上嘲笑别人的英语是不合适的。除此之外,我不认为修饰示例中的 cmets 有助于提高即使对流非常熟悉的人的可读性,也没有无用的返回变量。如果我在实际代码中遇到它们,我会考虑这两种噪音。凭借我对流的更多经验,我今天会选择保留原始换行符以提高可读性。没有人是完美的。我的目标是为新程序员提供一个明确的示例以及一个现实的示例。
      • 我不是在嘲笑你的英语。你的英语很好。我什至不明白你在说什么。是的,我同意 cmets 是多余的,第一个的格式要好得多。我的观点是,当可读性是一个非常重要的代码质量指标时,您似乎建议“为可读性而修饰”是不好的。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-01-28
      • 1970-01-01
      • 1970-01-01
      • 2016-08-28
      • 1970-01-01
      • 1970-01-01
      • 2013-08-29
      相关资源
      最近更新 更多