Как jvm classloader загружает класс, определенный внутри другого класса?

Как JVM загружает класс, определенный внутри другого класса?

Пример: Допустим, есть класс B, который определен внутри класса A.

package test.sample;
    Class A {
         // some instructions

         Class B {
             // few more instructions
         }
    }

В этом случае,

  1. Как загрузчик классов загружает класс B? (т. е. как он идентифицирует класс B?)
  2. Каким будет полное имя класса B?

person Adhi    schedule 11.06.2014    source источник


Ответы (1)


Внутренние классы — это функция языка Java, а не функция JVM. То есть компиляторы Java «сглаживают» структуру классов, поэтому JVM просто видит обычные классы, обычно с $ в именах. В этом случае будут классы test.sample.A и test.sample.A$B (последний является полным именем B). Анонимные внутренние классы получают имена, определяемые компилятором, обычно начинающиеся с 1 и увеличивающиеся: например, test.sample.A$6. Компилятор может добавлять методы с такими именами, как access$200, чтобы позволить охватывающему классу и внутреннему классу получать доступ к закрытым членам друг друга. (Обратите внимание, что $ разрешено, хотя и не рекомендуется, в именах определяемых пользователем классов и методов, поэтому наличие $ в имени не означает, что оно сгенерировано компилятором; для этого есть Синтетический атрибут и бит-модификатор ACC_SYNTHETIC, отображаемый отражательно через такие методы, как Class.isSynthetic()< /а>.)

JVM загружает эти классы точно так же, как и любой другой класс, обычно ища файл test/sample/A$B.class в каком-нибудь JAR-файле, но также, возможно, загружая их по сети, генерируя их на лету с помощью библиотеки для обработки байт-кода и т. д.

При создании файлов классов, которые ссылаются на внутренний класс (определение, содержание или просто использование), компиляторы Java выдают InnerClasses, определяющие отношения включения, для помощи в раздельной компиляции и отражении (Class.getDeclaringClass() и Class.getEnclosingClass()). Файлы классов для классов, определенных внутри метода, также содержат EnclosingMethod, относящийся к методу включения, для отражения (Class.getEnclosingMethod() и Class.getEnclosingConstructor()). Однако JVM проверяет синтаксическую правильность этих атрибутов только во время загрузки и компоновки; о несоответствиях не сообщается до тех пор, пока не будут фактически вызваны отражающие методы.

person Jeffrey Bosboom    schedule 04.07.2014