ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • [Java] Reflection(리플렉션)
    프로그래밍/Java 2021. 12. 29. 16:24
    반응형

    이 글은 혼자 학습한 내용을 바탕으로 작성되었습니다.

    틀리거나 잘못된 정보가 있을 수 있습니다.

    댓글로 알려주시면 수정하도록 하겠습니다.


    1. Reflection이란

    리플렉션이란 런타임 시점에 자바 코드 자체를 추상화하여 구체적인 클래스의 타입을 알지 못하여도 메소드나 속성 등 여러가지 작업들을 할 수 있도록 해주는 Java API 입니다.

     

    2. Reflection을 사용하는 기술

    • Spring Framework
    • Jackson
    • Hibernate

    3. Reflection 사용 방법

    forName 메소드
    Class<?> couponClass = Class.forName(패키지.클래스명);

    Class.forName 메소드를 이용하여 Class Object를 가져올 수 있습니다.

     

    forName 메소드의 파라미터로 패키지를 포함한 Class 명을 전달하면 해당 Class의 Class Object를 반환하여 줍니다.

     

    만약 패키지를 포함하지 않고 Class명만 파라미터로 전달 시 ClassNotFoundException이 Throw 됩니다.

     

    'Object'.class

    다른 방법으로는 .class를 이용하여 Class Object를 가져오는 방법이 있습니다.

     

    getConstructors, getConstructor 메소드

    모든 생성자는 Public으로 정의된 생성자만 가져올 수 있습니다.

    'ClassObject'.getConstructors();

    forName의 Class Object의 getConstructors 메소드를 통해 해당 Class의 정의되어 있는 모든 생성자를 가져올 수 있습니다.

     

    모든 생성자 메소드를 반환하므로 반환 타입은 Constructor[] 타입으로 반환 됩니다.

     

    'ClassObject'.getConstructor(생성자 파라미터 타입);

    forName으로 생성된 Class Object의 getConstructor 메소드는 여러 생성자들 중 파라미터로 전달한 타입들이 맞는 생성자 1개를 반환합니다.

     

    Package를 포함한 경우와 Class명만 전달한 경우에 대한 Test입니다.

     

    Class명만 전달한 경우는 ClassNotFoundException이 발생하는 것을 알 수 있으며 Package를 포함한 경우는 정상적으로 Class Object를 가져오는 것을 확인할 수 있습니다.

     

    getMethods, getMethod 메소드

    모든 메소드는 Public으로 정의된 메소드만 가져올 수 있습니다.

     

    'ClassObject'.getMethods();

    forName의 Class Object의 getMethods 메소드를 통해 해당 Class에 정의되어 있는 모든 메소드들을 가져올 수 있습니다.

     

    또한 getMethods 메소드는 Super Class의 메소드도 포함하여 반환 됩니다.

     

    Super Class의 메소드도 포함 되기 때문에 Java의 최상단인 Object Class에 포함되어 있는 메소드는 항상 포함되어 반환 됩니다.

     

    ※ Object Class

    • wait
    • equals
    • toString
    • hashCode
    • getClass
    • notify
    • notifyAll

    위 메소드 들이 포함되어 반환 됩니다.

     

    정의된 모든 메소드를 반환하므로 반환 타입은 Method[] 타입으로 반환 됩니다.

     

    'ClassObject'.getMethod(메소드명, 메소드파라미터 타입);

    forName으로 생성된 Class Object의 getMethod 메소드는 여러 메소드들 중 파라미터로 전달한 메소드명과 파라미터 타입이 맞는 메소드 1개를 반환합니다.

     

    Coupon Class는 생성자를 제외한 메소드는 총 7개 선언되어 있습니다.

     

    Coupon Class의 경우 총 7개의 메소드가 선언되어 있지만 테스트 결과를 보면 총 16개의 메소드가 반환된 것을 확인할 수 있습니다. 이건 Java의 모든 Class의 최상위 Class인 Object Class가 상속되어 있기 때문에 Object Class의 9개 메소드가 포함되어 반환 된 것입니다.

     

    getMethod는 반환 받고자 하는 Method의 명칭과 해당 Method의 파라미터 타입을 통해 해당 Method를 찾아 반환 해 줍니다. 테스트는 getDiscountAmount 메소드를 반환 받고자 하였으면 해당 메소드의 파라미터인 productPrice가 int 타입이므로 int.class를 전달 합니다.

     

    getMethod는 정의되지 않는 Method명을 전달 시 NoSuchMethodException을 Throw하는 것을 확인할 수 있습니다.

     

    getFields, getField 메소드

    모든 필드는 Public으로 정의된 필드만 가져올 수 있습니다.

    'ClassObject'.getFields()

    forName의 Class Object의 getFields 메소드를 통해 해당 Class의 정의되어 있는 모든 필드를 가져올 수 있습니다.

     

    모든 필드를 반환하므로 반환 타입은 Field[] 타입으로 반환 됩니다.

     

    'ClassObject'.getField(필드명)

     

    forName으로 생성된 Class Object의 getField 메소드는 여러 필드들 중 파라미터로 전달한 필드명과 동일한 필드 1개를 반환합니다.

     

    Coupon Class는 name필드만 Public으로 가지고 있습니다.

     

    필드가 Public인 경우와 Private인 경우에 대한 Test입니다.

     

    getFields의 경우 정의된 여러 필드 중 Public 필드는 name 하나 이므로 1개의 Field를 담은 배열이 반환됩니다.

     

    getField메소드를 통해 name필드를 가져온 경우 또한 name이 Public으로 선언되어 정상적으로 반환되는 것을 확인 할 수 있습니다.

     

    이번에는 Private으로 선언된 discount의 경우 NoSuchFieldException이 Throw되는 것을 확인할 수 있습니다.

     

    사용된 예제 코드는 Git에 있습니다.

    반응형

    '프로그래밍 > Java' 카테고리의 다른 글

    [Java] toString 메소드 재정의  (0) 2022.03.03
    [Java] Reflection Private  (0) 2022.01.11
    [Java] Reflection Invoke  (0) 2021.12.31
    [Java] 트랜잭션  (0) 2021.11.13

    댓글

Designed by Tistory.