클래스 로더를 사용하는 이유는 무엇입니까?
Java 언어에서는 프로그램 작동 중에 클래스 로딩이 완료됩니다. 이 전략은 클래스 로딩시 성능 오버 헤드를 약간 증가시킬 것이지만 Java 응용 프로그램에 높은 유연성을 제공합니다. 예를 들어:
1. 인터페이스 지향 응용 프로그램을 작성하고 구현 하위 클래스를 지정하기 전에 실행될 때까지 기다릴 수 있습니다.
2. 사용자는 클래스 로더를 사용자 정의하여 프로그램이 런타임시 프로그램 코드의 일부로 네트워크 또는 기타 장소에서 이진 스트림을로드 할 수 있습니다. (이것은 Android 플러그인, 동적 설치 및 APK 업데이트의 기초입니다)
수업 로딩의 전체 과정을 연구하는 이유는 무엇입니까?
클래스 로딩 메커니즘
JVM은 클래스 파일을 메모리에로드하고 데이터를 검사하고 구문 분석하고 초기화하고 마지막으로 JVM이 직접 사용할 수있는 Java 유형의 전체 프로세스를 형성합니다.
짐
클래스 파일의 바이트 코드 컨텐츠를 메모리에로드하고 정적 데이터를 메소드 영역의 런타임 데이터 구조로 변환하고 메소드 영역 클래스 데이터의 액세스 포털로 힙 에서이 클래스를 나타내는 java.lang.Class 객체를 생성하십시오. 이 프로세스에는 클래스 로더의 참여가 필요합니다.
링크
Java 클래스의 이진 코드를 JVM의 실행중인 상태로 결합하는 프로세스
초기화
<clinit>() 메소드를 실행하는 프로세스입니다. 클래스 생성자 <clinit>() 메소드는 컴파일러에 의해 생성됩니다. 클래스의 모든 클래스 변수의 할당 동작과 정적 명령문 블록 (static block)에서 문의 병합을 자동으로 수집합니다.<clinit>() 메소드가 다중 스레드 환경에서 올바르게 잠겨 있고 동기화되도록합니다.Example 1:
공개 클래스 demo01 {public static void main (String [] args) {a a = new a (); System.out.println (a.width); }} class a {public static int width = 100; // 정적 변수, 정적 필드 필드 static {System.out.println ( "정적 초기화 클래스 A"); 너비 = 300; } public a () {system.out.println ( "클래스 A의 객체 만들기"); }}분석 :
설명 :
스택, 힙 (생성 된 객체) 및 메모리의 메소드 영역 (실제로 특수 힙)이 있습니다.
1. JVM이 DEMO01을로드 할 때 먼저 메소드 영역에서 정적 데이터 (클래스 변수, 클래스 메소드, 코드 ...)를 형성합니다. 동시에, java.lang.Class 객체 (반사 객체)가 Demo01 클래스를 나타내는 힙에 형성됩니다. 물체를 통해 클래스 바이너리 구조에 액세스 할 수 있습니다. 그런 다음 변수 클래스 A 정보를로드하고 클래스 A를 나타내는 힙에 객체 A를 형성합니다.
2. 기본 메소드가 실행되면 기본 메소드 스택 프레임이 스택에 형성되고 하나의 메소드는 스택 프레임에 해당합니다. 기본 메소드가 다른 메소드를 호출하면 스택에서 하나씩 누릅니다. 주요 방법에는 로컬 변수 A 형이 있습니다. 처음에는 a의 값이 널입니다. 클래스 A의 생성자는 새로운 것을 통해 호출됩니다. a () 방법은 스택에서 생성되고 A 객체는 힙에 생성됩니다. 그런 다음 객체 주소는 스택에서 A에 지불됩니다. 현재 A에는 A 객체 주소가 있습니다.
3. A.Width가 호출되면 방법 영역 데이터가 호출됩니다.
클래스가 참조로로드되면 클래스는 한 번만로드됩니다.
클래스에 대한 적극적인 참조 (클래스 초기화가 확실히 발생합니다)
java.lang.reflect 패키지 메소드를 사용하여 클래스에 반사를 호출하십시오. 수업에 대한 수동적 참조 (클래스 초기화는 발생하지 않습니다)
Example 2:
공개 클래스 demo01 {static {system.out.println ( "정적 초기화 demo01"); } public static void main (string [] args)은 예외 {system.out.println ( "demo01의 기본 메소드!"); System.out.println (System.GetProperty ( "java.class.path")); // active reference // new a (); // system.out.println (a.width); // class.forname ( "com.sinosoft.test.a"); // 수동 참조 // System.out.println (a.max); // a [] as = new a [10]; System.out.println (b.width); // 클래스 B가로드되지 않습니다}} 클래스 B는 a {static {system.out.println ( "static initialization b")을 확장합니다. }} 클래스 A는 a_father {public static int width = 100; // 정적 변수, 정적 도메인 필드 공용 정적 최종 int max = 100; static {system.out.println ( "정적 초기화 클래스 A"); 너비 = 300; } public a () {system.out.println ( "클래스 A의 객체 만들기"); }} class a_father 확장 객체 {static {system.out.println ( "static initialization a_father"); }}요약
위는이 기사의 전체 내용입니다. 이 기사의 내용에 모든 사람의 연구 나 작업에 대한 특정 참조 가치가 있기를 바랍니다. 궁금한 점이 있으면 의사 소통을 위해 메시지를 남길 수 있습니다. Wulin.com을 지원 해주셔서 감사합니다.