21. 자바 반사 메커니즘 과 주해
10121 단어 자바 반사 메커니즘
Reflection is a feature in the Java programming language. It allows an executing Java program to examine or "introspect( )" upon itself, and manipulate( ) internal properties of the program. For example, it's possible for a Java class to obtain the names of all its members and display them.
The ability to examine and manipulate a Java class from within itself may not sound like very much, but in other programming languages this feature simply doesn't exist. For example, there is no way in a Pascal, C, or C++ program to obtain information about the functions defined within that program.
One tangible( ) use of reflection is in JavaBeans, where software components can be manipulated visually via( ) a builder tool. The tool uses reflection to obtain the properties of Java components (classes) as they are dynamically loaded.
java , ( ) 。 java 。 java , C C++ 。 Pascal、C、C++ ; JavaBean , javaBean , javaBean 。
반사 메커니즘 을 이해 하려 면 반드시 java. lang. Class 에 대해 알 아야 한다. 18, 19 장 참조.
먼저 Class 의 구조 기 를 보십시오.
/*
* Constructor. Only the Java Virtual Machine creates Class
*/
private Class() {}
주석 은 이 종 류 는 JVM 이 만 들 어 졌 기 때문에 귀 찮 게 하지 않 아 도 된다 는 것 을 명확 하 게 알려 주 었 다.만약 우리 가 하나의 유형의 정 보 를 얻 게 된다 면 반 사 를 이용 하여 각종 구성원 과 방법 을 얻 을 수 있 을 것 이다.(비고: Class 는 JDK 1.5 버 전부터 팬 서 비 스 를 더 많이 받 았 습 니 다) 그러면 우 리 는 어떻게 한 가지 유형의 정 보 를 얻 을 수 있 습 니까?만약 에 우리 에 게 Role 류 가 있다 고 가정 하면:
package org.Smart;
/*
* a class Role has some methods and attribute
*/
public class Role {
public Role(){}
public Role(String s){}
private String s;
private int x;
public void fun1(String s){
System.out.println(s);
}
public void fun2(){
System.out.println("ok");
}
}
테스트:
public class Sample {
@SuppressWarnings("rawtypes")
public static void main(String...s) {
Class c=Role.class;
Method[] m=c.getDeclaredMethods();
for(int x=0;x<m.length;x++){
System.out.println(m.toString());
}
}
}
Class 인 스 턴 스 를 가 져 오 는 몇 가지 방법:
Class cls1 = Role.class;
Class cls2 = Class.forName("org.Smart.Role");
Role r=new Role();
Class cls3=r.getClass();
Class cls4= Boolean.TYPE; //
두 번 째 방식 에서 forName 의 인 자 는 반드시 완전한 클래스 (패키지 이름 + 클래스 이름) 이 고 이 방법 은 이상 을 포착 해 야 합 니 다.이제 cls 1 을 얻 으 면 Role 클래스 의 인 스 턴 스 를 만 들 수 있 습 니 다. Class 의 new Instance 방법 을 이용 하여 호출 클래스 의 기본 구조 기 에 해당 합 니 다.
Class c;
try {
c = Class.forName("org.Smart.Role");
Role r=(Role) c.newInstance(); // Role r=new Role(); newInstance() Role
r.fun2();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
구조 기 획득: getConstructors / getDeclared Constructors (사유 / 사유 포함 하지 않 음) 사유 또는 공유 로 설정 할 수 있 습 니 다.
획득 속성: getFields / getDeclaredFields
획득 방법: getMethods / getDeclaredMethods
클래스 호출 방법:
Class c= Role.class;
Object obj=c.newInstance();
Method fun=c.getDeclaredMethod("fun1", String.class); // fun1 null,
fun.invoke(obj, "e");// null,
속성 값 설정:
Field f=c.getDeclaredField("x");
f.setInt(obj, 32); //int x; public ,setInt int ;
여기까지 자바. lang. reflect 패키지 의 Method / Field / constructor 류 를 사 용 했 습 니 다. 이 종 류 는 모두 Class. get () 을 받 아 얻 은 방법 / 속성 / 구조 기 이 고 가장 중요 한 운용 도 있 습 니 다. jvm 핵심 중 하나 인 Proxy 대 리 는 다음 장 내용 에서 설명 할 것 입 니 다.
Class 의 기타 중요 한 방법:
static Class<?> forName(String name, boolean initialize, ClassLoader loader) //Class
static Class<?> forName(String className)//
<A extends Annotation>A getAnnotation(Class<A> annotationClass)
Annotation[] getAnnotations()
ClassLoader getClassLoader()//
Class<?>[] getInterfaces() //
String getName()//
Package getPackage() //
Class<? super T> getSuperclass()//
다음은 이어서 주 해 를 말씀 드 리 겠 습 니 다.
JDK 5 에는 소스 코드 의 주석 (annotation) 이라는 메커니즘 이 도입 됐다.주 해 는 자바 소스 코드 에 기능 적 인 실현 코드 를 포함 할 수 있 을 뿐만 아니 라 메타 데이터 도 추가 할 수 있 게 한다.주해 의 기능 은 코드 중의 주석 과 유사 하 며, 다른 것 은 주해 가 코드 기능 을 제공 하 는 설명 이 아니 라 프로그램 기능 을 실현 하 는 중요 한 구성 부분 이다.자바 주 해 는 이미 많은 프레임 워 크 에서 광범 위 하 게 사용 되 어 프로그램의 설정 을 간소화 하 는 데 사용 되 었 다.
자바 주 해 는 자바 레이 블 이 라 고도 부 릅 니 다. 자바 는 방법, 클래스, 파라미터, 가방, 도 메 인 및 변수 등에 대해 표준 을 추가 할 수 있 는 메커니즘 을 제공 합 니 다 (즉, 일부 정 보 를 첨부 합 니 다).또한 앞으로 어느 시간 대 에 반 사 를 통 해 표 시 된 정 보 를 추출 하여 사용 할 수 있 도록 한다.
자 바 는 1.5 버 전 이후 기본적으로 세 개의 레이 블 을 내장 합 니 다.
@ Override: 방법 위 에 만 사용 할 수 있 습 니 다. 다른 사람 에 게 이 방법 은 부 류 를 바 꾸 는 것 입 니 다.
@ Deprecated: 오래된 API 를 사용 하지 말 것 을 권장 합 니 다. 컴 파일 할 때 경고 메 시 지 를 사용 합 니 다. 프로그램의 모든 요소 에 설정 할 수 있 습 니 다.
@ Suppress Warnings: 이 유형 은 경고 메 시 지 를 잠시 닫 을 수 있 습 니 다.
그러나 이 세 가지 표시 만 으로 는 우리 가 개발 할 때의 수 요 를 만족 시 킬 수 없다.그래서 자바 에 서 는 사용자 정의 주 해 를 사용 할 수 있 습 니 다.
어떤 측면 에서 볼 때 주 해 를 XML 요소 로 볼 수 있 고 이 요 소 는 서로 다른 미리 정 의 된 속성 을 가 질 수 있다.속성의 값 은 이 요 소 를 설명 할 때 스스로 지정 할 수 있 습 니 다.코드 에 주 해 를 사용 하면 일부 메타 데 이 터 를 XML 파일 에서 코드 자체 로 옮 겨 한 곳 에서 관리 하고 유지 하 는 것 과 같 습 니 다.
어떻게 스스로 주 해 를 설계 합 니까?
먼저 rt. jar 아래 자바. lang. annotation 가방 을 보 세 요.
Target.class
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.ANNOTATION_TYPE)
public @interface Target { //@Target , ANNOTATION_TYPE
ElementType[] value();
}
//Java , ,
//@Documented JavaDoc 32 public @interface Documented {
//@Inheried
//@Retention , 。 RetentionPoicy :public @interface Retention{
//RetentionPolicy.SOURCE: java , public enum RetentionPolicy {
//RetentionPolicy.CLASS: class , VM ( )
//RetentionPolicy.RUNTIME: ,VM ,
//@Target , 。 ElementType
//ElementType.CONSTRUCTOR: public enum ElementType {
//ElementType.FIELD: 、 、 ( enum )
//ElementType.LOCAL_VARIABLE:
//ElementType.METHOD:
//ElementType.PACKAGE:
//ElementType.PARAMETER:
//ElementType.TYPE: 、 ( ) enum
//ElementType.ANNOTATION_TYPE Annotation type declaration
@interface 는 하나의 키워드 입 니 다. 주 해 를 디자인 할 때 하나의 유형 을 @ interface 로 정의 해 야 합 니 다. class 나 interface 키 워드 를 사용 할 수 없습니다. @ Retention 은 주 해 를 설명 하 는 보존 정책 입 니 다. CLASS, RUNTIME, SOURCE 등 세 가지 속성 이 있 습 니 다. 주 해 는 바이트 코드. class 파일, JVM 실행 시간 과 소스 코드. 자바 파일 에 저 장 됩 니 다.런 타임 이 라 고 밝 혀 졌 을 때 만 반사 메커니즘 을 통 해 주석 정 보 를 얻 을 수 있 습 니 다. @Target 은 어떤 요소 형식 을 추가 할 수 있 는 지 설명 하 는 데 사 용 됩 니 다.
SOURCE 는 이 Annotation 형식의 정 보 는 프로그램 소스 코드 에 만 남아 있 고 소스 코드 가 컴 파일 을 거 친 후에 Annotation 의 데 이 터 는 사라 지고 컴 파일 된 class 파일 에 저장 되 지 않 습 니 다. ClASS 는 이 Annotation 형식의 정 보 를 프로그램 원본 에 저장 하 는 동시에 컴 파일 된. class 파일 에 도 저장 합 니 다. 실행 할 때 이 정 보 를 가상 머 신 (JVM) 에 불 러 오지 않 습 니 다. Annotation 형식의 Retention 값 을 설정 하지 않 았 을 때 시스템 기본 값 은 CLASS 입 니 다. RUNTIME 은 원본 코드, 컴 파일 된 class 파일 에 정 보 를 저장 하고 실행 할 때 이 정 보 를 JVM 에 불 러 옵 니 다.
@Documented 의 목적 은 이 Annotation 형식의 정 보 를 자바 API 설명 문서 에 표시 하 는 것 입 니 다.추가 되 지 않 으 면 javadoc 를 사용 하여 API 문 서 를 생 성 할 때 이 형식 으로 생 성 된 정 보 를 찾 을 수 없습니다.
Annotation 의 데 이 터 를 하위 클래스 에 계승 하려 면 @ Inherited 라 는 Annotation 형식 을 사용 합 니 다.
@ Override 주 해 를 살 펴 보 겠 습 니 다.
4. 567913. 위 에서 알 수 있 듯 이 이 주 해 는 방법 전에 만 사용 할 수 있 고 소스 코드 에 저장 할 수 있 으 며 @ T.. @ R 을. class 파일 에 저장 하지 않 습 니 다. 그러나 역 컴 파일 을 통 해 이 두 주 해 를 출력 할 수 있 습 니까?
@ Override 를 사용 할 때 하나의 성명 만 있 으 면 됩 니 다. 매개 변 수 를 전달 하지 않 고 태그 주석 (marker annotation) 이 라 고 부 르 며 특정한 설정 의 미 를 대표 합 니 다.
@ Suppress Warnings ("xxxtype") 를 사용 하여 매개 변 수 를 전달 합 니 다.사실은 이름 값 대구 문 입 니 다. value = "xxxtype" 은 value = 이 문자열 을 생략 합 니 다.
모든 Annotation 은 자바. lang. annotation 이라는 인 터 페 이 스 를 자동 으로 계승 하기 때문에 다른 클래스 나 인 터 페 이 스 를 계승 할 수 없습니다. ;Public 또는 기본 값 (default) 두 개의 접근 권한 으로 만 이 주해 류 를 설명 할 수 있 습 니 다.방법의 반환 값 은 기본 형식 (주석 에서 전 달 된 매개 변수 와 연결) byte, short, char, int, long, float, double, boolean 과 String, Enum, Class, annotations 등 데이터 형식 과 이 유형의 배열 만 있 을 수 있 습 니 다.구성원 변수 가 하나 밖 에 없다 면 변수 이름 을 'value' 로 설정 하고 괄호 String value () 를 추가 하 는 것 이 좋 습 니 다. 이렇게 설명 할 때 value 필드 를 생략 할 수 있 습 니 다. 형식적 으로 는 참여 방법 이 없습니다.여러 구성원 변수 뒤에 () 를 추가 해 야 합 니 다. int x () 와 같 습 니 다.
설명 주해 류 를 스스로 설계 합 니 다:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.SOURCE)
public @interface Override {
}
설명 설명 사용 하기:
@Target(ElementType.TYPE) // , ;
@Retention(RetentionPolicy.RUNTIME) // jvm
public @interface Description {
String info();
String str();
}
주석 보기:
@Description(info="skx",str="good name!!")
public class UseDescription {
}
주석 처리 과정:import com. sun. mirror. apt. annotationProcessorFactory 를 깊이 연구 하고 싶 었 습 니 다.@ Deprecated 에 게 알려 졌 습 니 다. 주석 과정 에 대한 상세 한 설명 을 아 는 친구 가 있 으 면 가르쳐 주 십시오.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
자바 반사:자바 방법 반사 기본 조작앞에서 우 리 는 클래스 유형 을 통 해 클래스 에 해당 하 는 방법 을 배 웠 습 니 다.그러면 우 리 는 자바 반사 체 제 를 통 해 클래스 의 방법 을 호출 하 는 등 기본 적 인 조작 을 할 수 있 습 니까?...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.