允许特定类的实例只由Java中的另一个类创建?

时间:2013-11-16 01:44:38

标签: java singleton access-modifiers

假设我有两个A和B类,我想这样做,以便B的实例只能在A和B本身中创建。我不希望任何其他类(包括A的子类)被允许创建B的实例。有没有办法在Java中这样做?

如果我不清楚我想要做什么,这里有一些代码:

public class A {
    B instance;
    public A(){
        // Still allows for subclasses to access B
        instance = B.getInstance((Object)this);
    }
}

这是我想要限制其构造的类:

public class B {

    // If I make this public all classes can create it, but
    // if I make it private without any getter methods then
    // no other classes but itself can create it
    private B(){}

    // Problem with this is that subclasses of  A
    // can also create instances of B
    public static B getInstance(Object o){
        if(o instanceof A)
            return new B();
        else
            return null;
    } 
}

我已尝试使用Google搜索并在StackOverflow上搜索可能的解决方案,但我发现最接近的是使用带有修改的getInstance()方法的Singleton设计模式,以确保只有具有特定类型的类才能访问类B的实例虽然这种方法运行得相当好,但它仍然允许任何扩展A的子类来获取B的实例。有没有办法阻止这种情况发生,或者如果子类不能做,它会破坏子类的整个要点它的超类可以做什么?

4 个答案:

答案 0 :(得分:7)

  

假设我有两个A和B类,我想这样做,以便B的实例只能在A和B本身中创建。我不希望任何其他类(包括A的子类)被允许创建B的实例。

你可以使B成为A类的私人内部类。

答案 1 :(得分:1)

  

虽然这种方法运行得相当好,但它仍然可以启用任何子类   扩展A来获取B的实例。有没有办法阻止它   发生或者它会破坏子类化的整个点,如果a   子类不能做它的超类可以做的事情吗?

如果你不希望你的A类被子类化,你可以让A类最终,或者可以有A的私有构造函数。尽管如前面的答案中所建议的那样,最好创建私有内部类。

public final class A {
    B instance;
    public A(){
        // Still allows for subclasses to access B
        instance = B.getInstance((Object)this);
    }
}

答案 2 :(得分:0)

如果创建类不是B

,则此类将抛出异常
class A {

    A() {
        new SecurityManager() {
            {
                if (getClassContext()[1] != B.class) {
                    throw new IllegalStateException();
                }
            }
        };
    }
...

即使使用反射也无法打破

答案 3 :(得分:0)

A可以向B提供只有A才能拥有的内容。例如

public class A
{
    public static class Pass
    {
        private Pass(){}

只有A才能创建A.Pass个对象。如果此类对象仅从A传输到B,则其他任何人都无法抓住这些对象并伪装成A

public class B
{
    public static B getInstance(A.Pass token)
    {
        if(pass==null) 
            throw ...      
        else
            caller must be A