Java 单例类的多个实例。。。非常奇怪的行为

Java 单例类的多个实例。。。非常奇怪的行为,java,android,singleton,Java,Android,Singleton,我有一个实现Singleton模式的类。我需要在一个活动和一个片段(由活动托管)中创建这个类的实例 奇怪的是,如果活动是第一个创建singleton类实例的,当我尝试从片段中检索该实例时,它会创建另一个实例 以下是singleton类的代码: public class NotificationCenter { private NotificationCenter() { } // useless for this question private class MyOb

我有一个实现Singleton模式的类。我需要在一个活动和一个片段(由活动托管)中创建这个类的实例

奇怪的是,如果活动是第一个创建singleton类实例的,当我尝试从片段中检索该实例时,它会创建另一个实例

以下是singleton类的代码:

public class NotificationCenter {
    private NotificationCenter() {

    }

// useless for this question
    private class MyObservable extends Observable {
        @Override
        protected void setChanged() {
            super.setChanged();
        }
    }

    // useless for this question
    private class MyObserver implements Observer {
        String name;
        Notificable notificable;

        public MyObserver(String name, Notificable notificable) {
            this.name = name;
            this.notificable = notificable;
        }

        @Override
        public void update(Observable observable, Object data) {
            notificable.notificationReceived(name, data);
        }       
    }

    private static NotificationCenter defaultCenter = null;
    private HashMap<String, MyObservable> observables;

    public static synchronized NotificationCenter defaultCenter() {
        if (defaultCenter==null) {
            defaultCenter = new NotificationCenter();
            defaultCenter.observables = new HashMap<String, MyObservable>();
        }

        return defaultCenter;
    }

    public void addObserver(String notification, Notificable notificable) {
        MyObservable observable = observables.get(notification);
        if (observable==null) {
            observable = new MyObservable();
            observables.put(notification, observable);
        }
        MyObserver observer = new MyObserver(notification, notificable);
        observable.addObserver(observer);
    }

    public void removeObserver(String notification, Observer observer) {
        MyObservable observable = observables.get(notification);
        if (observable!=null) {         
            observable.deleteObserver(observer);
        }
    }       

    public void postNotification(String notification, final Object object) {
        final MyObservable observable = observables.get(notification);
        if (observable!=null) {
            observable.setChanged();
            observable.notifyObservers(object);
        }
    }
}
公共类通知中心{
私人通知中心(){
}
//对这个问题没用
私有类MyObservable扩展了Observable{
@凌驾
受保护的void setChanged(){
super.setChanged();
}
}
//对这个问题没用
私有类MyObserver实现了Observer{
字符串名;
不可通知的不可通知的;
公共MyObserver(字符串名称,Notifiable Notifiable){
this.name=名称;
this.notifiable=不可通知;
}
@凌驾
公共无效更新(可观测、对象数据){
notificationReceived(名称、数据);
}       
}
私有静态NotificationCenter defaultCenter=null;
私有HashMap可观测;
公共静态同步通知中心defaultCenter(){
if(defaultCenter==null){
defaultCenter=新建通知中心();
defaultCenter.observables=新HashMap();
}
返回默认中心;
}
public void addObserver(字符串通知,notifiable notifiable){
MyObservable observable=observables.get(通知);
if(可观察==null){
可观察=新的MyObservable();
可观察的。放置(通知,可观察);
}
MyObserver observer=新的MyObserver(通知,可通知);
可观察的。添加观察者(观察者);
}
public void removeObserver(字符串通知,观察者){
MyObservable observable=observables.get(通知);
如果(可观察!=null){
可观察的。删除观察者(观察者);
}
}       
公共void postNotification(字符串通知,最终对象){
最终MyObservable observable=observables.get(通知);
如果(可观察!=null){
setChanged();
观察者(对象);
}
}
}
我必须考虑一些我不喜欢的事情吗?
对defaultCenter()方法的所有调用都是在主线程上进行的。

首先,您的代码甚至没有编译

 map.put(k,v); // not add
第二个,我在构造函数中添加了一个
println()

private HashMap<String, String> map;
private Singleton() {
    System.out.println("Singleton Constructor");
    map = new HashMap<String, String>();
}
结果是

Singleton Constructor
One instance

如果您对错误感到不满,请发布您的实际代码(因为此处的代码显然不正确)。

正如您所说,您的代码不是线程安全的。除非单个实例的实例化成本很高,否则只需预先初始化它即可

class Singleton {
    private static Singleton instance = new Singleton();

你怎么知道它是不同的呢?因为我从调试器中看到它从创建指令(instance=new Singleton();)传递了两次,而且还考虑了其他因素。我确信它会两次创建singleton实例,除非你把类装入器搞砸了,否则这只会是线程安全问题……我在两个非常不同的时刻调用getInstance方法(也是在几分钟之后)。另外,我在活动中多次调用getInstance方法,然后当我在片段中调用它时,它会再次创建实例。。。我知道你认为我很愚蠢但我知道我在说什么,只是这很奇怪,这是我在用Java开发多年后第一次遇到这个问题。@Massimo我不熟悉android的线程模型,但如果活动和片段不在同一个线程上运行,或者如果你在从另一个线程调用的侦听器中调用
getInstance
,就会发生这种情况如果在活动中调用getInstance方法两次或多次,则不会出现问题。问题是当我在活动中调用getInstance一次或多次后,第一次调用该片段上的getInstance时。
class Singleton {
    private static Singleton instance = new Singleton();