Looking for java Keywords? Try Ask4Keywords

Java Language Внедрение пользовательского классаLoader


пример

Каждый пользовательский загрузчик должен прямо или косвенно расширить класс java.lang.ClassLoader . Основными точками расширения являются следующие методы:

  • findClass(String) - перегружает этот метод, если ваш загрузчик классов следует стандартной модели делегирования для загрузки классов.
  • loadClass(String, boolean) - перегружает этот метод для реализации альтернативной модели делегирования.
  • findResource и findResources - перегружать эти методы для настройки загрузки ресурсов.

Методы defineClass которые отвечают за фактическую загрузку класса из массива байтов, являются final чтобы предотвратить перегрузку. Перед вызовом defineClass .

Вот простой, который загружает определенный класс из массива байтов:

public class ByteArrayClassLoader extends ClassLoader {
    private String classname;
    private byte[] classfile;

    public ByteArrayClassLoader(String classname, byte[] classfile) {
        this.classname = classname;
        this.classfile = classfile.clone();
    }

    @Override
    protected Class findClass(String classname) throws ClassNotFoundException {
        if (classname.equals(this.classname)) {
            return defineClass(classname, classfile, 0, classfile.length);
        } else {
            throw new ClassNotFoundException(classname);
        }
    }
}

Поскольку мы только переопределили метод findClass , этот пользовательский загрузчик классов будет вести себя следующим образом при вызове loadClass .

  1. Метод loadClass findLoadedClass вызывает findLoadedClass чтобы узнать, был ли класс с этим именем уже загружен этим загрузчиком классов. Если это удастся, результирующий объект Class возвращается запрашивающему.
  2. Метод loadClass затем передает родительскому загрузчику классов, вызывая его вызов loadClass . Если родитель может обработать запрос, он вернет объект Class который затем возвращается запрашивающему.
  3. Если родительский загрузчик классов не может загрузить класс, findClass затем вызывает наш метод override findClass , передавая имя загружаемого класса.
  4. Если запрашиваемое имя соответствует this.classname , мы вызываем defineClass для загрузки фактического класса из this.classfile байтов this.classfile . Затем возвращается возвращаемый объект Class .
  5. Если имя не ClassNotFoundException , мы бросаем ClassNotFoundException .