[java] Java에서 클래스 오브젝트가 다른 클래스 오브젝트의 서브 클래스인지 확인하십시오.

Java의 리플렉션 API로 놀고 있고 일부 필드를 처리하려고합니다. 이제 필드 유형을 식별하는 데 어려움을 겪고 있습니다. 문자열은 쉽습니다 myField.getType().equals(String.class). 파생되지 않은 다른 클래스에도 동일하게 적용됩니다. 그러나 파생 클래스를 어떻게 확인합니까? 예를 LinkedList들어의 하위 클래스입니다 List. isSubclassOf(...)extends(...)방법을 찾을 수 없습니다 . 나는 모든 getSuperClass()것을 밟고 혼자서 내 상류층을 찾아야합니까?



답변

이 방법을 원합니다 :

boolean isList = List.class.isAssignableFrom(myClass);

일반적으로, 여기서, List(전술)로 대체되어야 superclass하고 myClass교체해야subclass

로부터 의 JavaDoc :

Class객체가 나타내는 클래스 또는 인터페이스가 지정된 Class매개 변수가 나타내는 클래스 또는 인터페이스와 동일하거나 수퍼 클래스 또는 수퍼 인터페이스인지 판별합니다 . true그렇다면 반환 합니다. 그렇지 않으면를 반환합니다 false. 이 Class객체가 원시적 형을 나타내는 경우 ,이 메소드는 true지정된 Class파라미터가 정확하게이 Class객체 인 경우를 돌려줍니다 . 그렇지 않으면를 반환합니다 false.

참고:


관련 :

a) 객체가 컴파일 타임에 알고있는 클래스 또는 인터페이스 (하위 클래스 포함)의 인스턴스인지 확인하십시오.

boolean isInstance = someObject instanceof SomeTypeOrInterface;

예:

assertTrue(Arrays.asList("a", "b", "c") instanceof List<?>);

b) 객체가 런타임에만 알고있는 클래스 또는 인터페이스 (하위 클래스 포함)의 인스턴스인지 확인하십시오.

Class<?> typeOrInterface = // acquire class somehow
boolean isInstance = typeOrInterface.isInstance(someObject);

예:

public boolean checkForType(Object candidate, Class<?> type){
    return type.isInstance(candidate);
}


답변

또 다른 옵션은 instanceof입니다.

Object o =...
if (o instanceof Number) {
  double d = ((Number)o).doubleValue(); //this cast is safe
}


답변

instanceof 는 인스턴스, 즉 객체에서 작동합니다. 때때로 당신은 수업과 직접 일하기를 원합니다. 이 경우 Class 클래스 의 asSubClass 메서드를 사용할 수 있습니다 . 몇 가지 예 :

1)

    Class o=Object.class;
    Class c=Class.forName("javax.swing.JFrame").asSubclass(o);

JFrame은 Object의 하위 클래스이기 때문에 원활하게 진행됩니다. c는 JFrame 클래스를 나타내는 Class 객체를 포함합니다.

2)

    Class o=JButton.class;
    Class c=Class.forName("javax.swing.JFrame").asSubclass(o);

JFrame은 JButton의 하위 클래스가 아니기 때문에 java.lang.ClassCastException 이 시작됩니다 . c는 초기화되지 않습니다.

삼)

    Class o=Serializable.class;
    Class c=Class.forName("javax.swing.JFrame").asSubclass(o);

JFrame은 java.io.Serializable 인터페이스를 구현하기 때문에 순조롭게 진행됩니다. c는 JFrame 클래스를 나타내는 Class 객체를 포함합니다.

물론 필요한 수입품이 포함되어야합니다.


답변

이것은 나를 위해 작동합니다 :

protected boolean isTypeOf(String myClass, Class<?> superClass) {
    boolean isSubclassOf = false;
    try {
        Class<?> clazz = Class.forName(myClass);
        if (!clazz.equals(superClass)) {
            clazz = clazz.getSuperclass();
            isSubclassOf = isTypeOf(clazz.getName(), superClass);
        } else {
            isSubclassOf = true;
        }

    } catch(ClassNotFoundException e) {
        /* Ignore */
    }
    return isSubclassOf;
}


답변

이것은 @schuttek의 답변의 향상된 버전입니다. 프리미티브에 대해 false를 올바르게 리턴하고 (예 : isSubclassOf (int.class, Object.class) => false) 인터페이스를 올바르게 처리하기 때문에 (예 : isSubclassOf (HashMap.class, Map.class) => true) 개선되었습니다.

static public boolean isSubclassOf(final Class<?> clazz, final Class<?> possibleSuperClass)
{
    if (clazz == null || possibleSuperClass == null)
    {
        return false;
    }
    else if (clazz.equals(possibleSuperClass))
    {
        return true;
    }
    else
    {
        final boolean isSubclass = isSubclassOf(clazz.getSuperclass(), possibleSuperClass);

        if (!isSubclass && clazz.getInterfaces() != null)
        {
            for (final Class<?> inter : clazz.getInterfaces())
            {
                if (isSubclassOf(inter, possibleSuperClass))
                {
                    return true;
                }
            }
        }

        return isSubclass;
    }
}


답변

a Class<?>가 다른 클래스의 하위 클래스 인지 확인하는 재귀 적 방법 Class<?>

@To Kra답변 개선 된 버전 :

protected boolean isSubclassOf(Class<?> clazz, Class<?> superClass) {
    if (superClass.equals(Object.class)) {
        // Every class is an Object.
        return true;
    }
    if (clazz.equals(superClass)) {
        return true;
    } else {
        clazz = clazz.getSuperclass();
        // every class is Object, but superClass is below Object
        if (clazz.equals(Object.class)) {
            // we've reached the top of the hierarchy, but superClass couldn't be found.
            return false;
        }
        // try the next level up the hierarchy.
        return isSubclassOf(clazz, superClass);
    }
}


답변

//계승

    class A {
      int i = 10;
      public String getVal() {
        return "I'm 'A'";
      }
    }

    class B extends A {
      int j = 20;
      public String getVal() {
        return "I'm 'B'";
      }
    }

    class C extends B {
        int k = 30;
        public String getVal() {
          return "I'm 'C'";
        }
    }

//행동 양식

    public static boolean isInheritedClass(Object parent, Object child) {
      if (parent == null || child == null) {
        return false;
      } else {
        return isInheritedClass(parent.getClass(), child.getClass());
      }
    }

    public static boolean isInheritedClass(Class<?> parent, Class<?> child) {
      if (parent == null || child == null) {
        return false;
      } else {
        if (parent.isAssignableFrom(child)) {
          // is child or same class
          return parent.isAssignableFrom(child.getSuperclass());
        } else {
          return false;
        }
      }
    }

// 코드 테스트

    System.out.println("isInheritedClass(new A(), new B()):" + isInheritedClass(new A(), new B()));
    System.out.println("isInheritedClass(new A(), new C()):" + isInheritedClass(new A(), new C()));
    System.out.println("isInheritedClass(new A(), new A()):" + isInheritedClass(new A(), new A()));
    System.out.println("isInheritedClass(new B(), new A()):" + isInheritedClass(new B(), new A()));


    System.out.println("isInheritedClass(A.class, B.class):" + isInheritedClass(A.class, B.class));
    System.out.println("isInheritedClass(A.class, C.class):" + isInheritedClass(A.class, C.class));
    System.out.println("isInheritedClass(A.class, A.class):" + isInheritedClass(A.class, A.class));
    System.out.println("isInheritedClass(B.class, A.class):" + isInheritedClass(B.class, A.class));

//결과

    isInheritedClass(new A(), new B()):true
    isInheritedClass(new A(), new C()):true
    isInheritedClass(new A(), new A()):false
    isInheritedClass(new B(), new A()):false
    isInheritedClass(A.class, B.class):true
    isInheritedClass(A.class, C.class):true
    isInheritedClass(A.class, A.class):false
    isInheritedClass(B.class, A.class):false