Одиночный class с несколькими различными загрузчиками classов

Например, у меня есть class Singleton со статическим полем:

 public class Singleton { private static Singleton instance; // other code, construct, getters, no matter } 

Я могу загрузить этот class дважды с помощью двух разных загрузчиков classов. Как я мог избежать этого? Это опасно и опасно.

Кроме того, если я устанавливаю экземпляр в значение null, будет ли он установлен равным null для обоих classов?

 Singleton singleton = Singleton.getInstance(); singleton = null; 

Если вам нужен настоящий Singleton для загрузчиков classов, тогда вам нужен общий родитель для загрузки рассматриваемого classа, или вам нужно указать загрузчик classов самостоятельно.

Обновление: из комментария от @Pshemo ниже справедливой части содержимого в блоге ниже может быть получена непосредственно из статьи JavaWorld . Я оставил запись в блоге, так как он все равно может помочь кому-то, но его ценность – узнать, откуда взялся контент.

Оригинал: есть запись в блоге, которая дает вам способ сделать это »(хотя я и не пробовал!), И выглядит довольно разумно

Как указано ниже, fragment кода из моей ссылки выше – я предлагаю вам посетить блог, но для полного контекста:

 private static Class getClass(String classname) throws ClassNotFoundException { ClassLoader classLoader = Thread.currentThread().getContextClassLoader(); if(classLoader == null) classLoader = Singleton.class.getClassLoader(); return (classLoader.loadClass(classname)); } 

Это хак, злоупотребляющий тем фактом, что Properties extends Map , старое неудачное дизайнерское решение.

 public final class JvmWideSingleton { private static final JvmWideSingleton INSTANCE; static { // There should be just one system class loader object in the whole JVM. synchronized(ClassLoader.getSystemClassLoader()) { Properties sysProps = System.getProperties(); // The key is a String, because the .class object would be different across classloaders. JvmWideSingleton singleton = (JvmWideSingleton) sysProps.get(JvmWideSingleton.class.getName()); // Some other class loader loaded JvmWideSingleton earlier. if (singleton != null) { INSTANCE = singleton; } else { // Otherwise this classloader is the first one, let's create a singleton. // Make sure not to do any locking within this. INSTANCE = new JvmWideSingleton(); System.getProperties().put(JvmWideSingleton.class.getName(), INSTANCE); } } } public static JvmWideSingleton getSingleton() { return INSTANCE; } } 

Это можно сделать параметризованным, но тогда инициализация будет ленивой и перейдите к getSingleton() .

Properties – это Hashtable based, поэтому он является streamобезопасным (согласно документации). Таким образом, можно использовать props.computeIfAbsent() . Но мне это нравится больше.

Также читайте здесь: Область свойств Java-системы

Я просто написал это, и есть шанс, что я кое-что упустил, что помешало бы этому работать.

  • Существуют ли жизнеспособные альтернативы шаблону Singleton в GOF?
  • Контекст Singleton Per Call (веб-запрос) в Unity
  • Моностат против Синглтона
  • Шаблон для ленивого streamобезопасного создания одноэлементов в java
  • Когда сборщик мусора стирает экземпляр объекта, который использует шаблон Singleton?
  • Когда должен быть создан / открыт экземпляр EntityManagerFactory?
  • Singleton через экземпляр JVM или приложения или экземпляр Tomcat
  • Явная блокировка Java
  • Как избежать нескольких экземпляров формы Windows в c #
  • Почему внедрение шаблона Singleton в Java-коде (иногда) считается анти-шаблоном в Java-мире?
  • Как создать class singleton
  • Давайте будем гением компьютера.