获取对象的单个实例

时间:2010-08-05 14:50:37

标签: java

假设我有一个班级A,此班级有一个列表l。还有一个B类扩展A,可以访问列表l,如下所示。在我的程序中,必须只有一个类B的实例(我使用的是Singleton模式),并且List l也必须只有一个实例,所以我这样做像这样:

public abstract class A {

    protected List<String> l;

    public A() {}

    protected synchronized List<String> getList() {
        if (l == null)
            l = new LinkedList<String>();
        return l;
    }
}

//---

public class B extends A {

    private static B instance;

    private B() {
        super();
    }

    public static synchronized B getInstance() {
        if (instance == null)
        instance = new B();
        return instance;
    }
}

我想做的是:

B的一个例子中:

System.out.println(super.getList().size()); //must print 0
super.getList().add("a");
System.out.println(super.getList().size()); //will print 1

B的另一个例子中:

System.out.println(super.getList().size()); //should print 1, cause i've already
                                            //added "a", but prints 0
super.getList().add("b");
System.out.println(super.getList().size()); //should print 2, but prints 1

但这并不像预期的那样有效。我究竟做错了什么?任何人都可以帮助我吗?


编辑:

嗨,比尔蜥蜴,这是两个类:

public abstract class A {
    protected static List<String> l;

    public A() {}

    protected static synchronized List<String> getList() {
        if (l == null)
            l = new LinkedList<String>();
        return l;
    }
}

//---

public class B extends A {
    private static B instance;

    private B() {
        super();
    }

    public static synchronized B getInstance() {
        if (instance == null)
            instance = new B();
        return instance;
    }

    public void metodo() {
        System.out.println(super.getList().size());
        super.getList().add("a");
        System.out.println(super.getList().size());
    }
}

这就是我创建B实例的方式:

public class ClassTeste {
    public static void main(String[] args) {
        B b = B.getInstance();
        b.metodo();
    }
}

4 个答案:

答案 0 :(得分:1)

如果您有多个B实例,那么它不是单身人士。(您可能需要参考)

你为什么不这样做:

public abstract class A {

    protected List l = new LinkedList();

    public A() {}

    protected List getList() {
        return l;
    }
}
仅在实例化A时(即,实例化B时)才会实例化

'l'。

public class B extends A {

    private static B instance = new B();

    private B() {
        // Don't need this, implicitly use no-args super-constructor by default
        // super();
    }

    public static B getInstance() {
        return instance;
    }
}

'instance'只会在第一次引用B类时实例化,所以你可能会很好。

答案 1 :(得分:1)

这对我有用。

B b1 = B.getInstance();
B b2 = B.getInstance();

b1.metodo();
b2.metodo();

我得到以下输出。

  

0
  1
  1
  2

b1.metodo()的调用是在添加“a”一次后打印空列表的大小和大小。对b2.metodo()的调用再次打印相同的尺寸,然后再次添加“a”后的新尺寸。

答案 2 :(得分:1)

我使用以下主要方法

运行您的主要修订代码
public static void main(String[] args) {
 B b1 = B.getInstance();
 b1.metodo();

 B b2 = B.getInstance();
 b2.metodo();
}

并获得以下输出,与您要查找的内容相匹配

0
1
1
2

答案 3 :(得分:1)

单身人士只适用于该计划的生命。并且它不会在您的程序的其他实例之间共享。

听起来你希望它运行一次并获得1的输出,然后退出,然后再次运行并获得2的输出。或者运行两个程序并继续输出1,另一个输出2 。

这仅适用于使用线程而非整个进程的情况,并且每次终止进程并启动新进程时它仍会重置。