如何在Java中构造一个不可实例化的AND不可继承的类

问题描述 投票:13回答:3

问题就是这一切。我知道Singleton模式(同类的最终版)是一个解决方案。我们还有其他可能的方法吗?抽象类使其不可实例化。最终使它成为不可继承的。我们如何结合两者?

public final class SingletonObject
{
  private SingletonObject()
  {
    // no code req'd
  }

  /*public static SingletonObject getSingletonObject()
  {
    if (ref == null)
        // it's ok, we can call this constructor
        ref = new SingletonObject();        
    return ref;
  }*/

  public Object clone()
    throws CloneNotSupportedException
  {
    throw new CloneNotSupportedException(); 
    // that'll teach 'em
  }

  private static SingletonObject ref;
}

代码参考:http://www.javacoffeebreak.com/articles/designpatterns/index.html

java
3个回答
36
投票

使构造函数private

public final class Useless {
    private Useless() {}
}

私有构造函数是面向对象的常规解决方案。但是,仍然可以使用反射来实例化这样的类,如下所示:

Constructor<Useless> con = Useless.class.getDeclaredConstructor();
con.setAccessible(true); // bypass "private"
Useless object = con.newInstance();

要防止反射工作,请从构造函数中抛出异常:

public final class Useless {
    private Useless() {
        throw new UnsupportedOperationException();
    }
}

6
投票

你的意思是只有静态方法的类?类不能是最终的和抽象的。但是你可以使用私有构造函数使它不是即时的。

final class StaticOnly {

    private StaticOnly() {
        throw new RuntimeException("Do not try to instantiate this");
    }

    public static String getSomething() {
       return "something";
    }
}

下面的例子将起作用。你不会实例化它,因为它是抽象的。你不会继承它,因为没有办法从外部子类调用超级构造函数(只有内部子类可以工作)

abstract class StaticOnly {

    private StaticOnly() {}

    public static String getSomething() {
         return "something";
    }
}

枚举也会奏效

enum StaticOnly {
    S;

    public static String getSomething() {
        return "something";
    }
}

但它总是至少有一个实例(这里是S)。


2
投票

我会使用最简单的Singleton模式

enum Singleton {
    INSTANCE;
}

enum类型是非实例和不可继承的,类初始化是惰性和线程安全的。

要声明永远不应该有实例,您也可以使用枚举

enum Utilities {
    ; // no instances

    // add static methods here
}
© www.soinside.com 2019 - 2024. All rights reserved.