静态类和单例模式之间存在什么实际的区别?

两者都可以在没有实例化的情况下调用,两者都只提供一个“实例”,而且都不是线程安全的。还有其他区别吗?


当前回答

真正的答案是Jon Skeet在这里的另一个论坛上给出的。

单例允许访问单个已创建实例-该实例(或而是对该实例的引用)可以作为参数传递给其他方法,并视为正常对象静态类只允许静态方法。

其他回答

在许多情况下,这两者没有实际差异,特别是如果单例实例从未更改或更改非常缓慢,例如保持配置。

我想说,最大的区别是单例仍然是一个普通的JavaBean,而不是专门的仅静态Java类。正因为如此,单身汉在很多情况下都被接受;它实际上是默认的Spring框架的实例化策略。消费者可能知道也可能不知道它是一个被传递的单例,它只是把它当作一个普通的Javabean。如果需求发生变化,而单例需要成为原型,正如我们在Spring中经常看到的那样,它可以完全无缝地完成,而无需对消费者进行一行代码更改。

前面有人提到,静态类应该是纯过程的,例如java.lang.Math。在我看来,这样的类永远不应该被传递,它们永远不应该将静态final以外的任何属性作为属性。对于其他一切,使用单例,因为它更灵活,更易于维护。

从客户端的角度来看,静态行为对客户端来说是已知的,但是Singleton行为可以对客户端隐藏完成。客户可能永远不会知道,他一次又一次地玩弄着一个实例。

下面是静态类和单例之间的一些主要区别:

1.Singleton是一种模式,而不是像static那样的关键字。因此,对于创建静态类,静态关键字就足够了,而对于单例,则需要为单例编写逻辑。

2.单例类必须具有私有的默认实例构造函数,而静态类不能包含任何实例构造函数。

3.静态类既不实例化也不扩展,而单例类可以实例化。

4.静态类是隐式密封的,但单例类必须修饰为显式密封的。

5.单例可以实现接口或从另一个类继承,但静态类既不实现接口,也不从任何其他类扩展。

6.我们不能用静态类实现依赖注入,但单例类可以实现DI,因为它可以是接口驱动的。静态类的作用域位于应用程序域级别,因为它由CLR管理,而单例对象的作用域则跨越应用程序生命周期。

7.静态类不能有任何析构函数,但单例类可以定义析构函数。

8.单例类实例可以作为参数传递给另一个方法,而静态类不能传递,因为它只包含静态成员。

Singleton的被实例化。只是只有一个实例被创建过,因此在Singleton中只有一个。

另一方面,静态类无法实例化。

在单例模式中,可以将单例创建为派生类型的实例,但不能使用静态类。

快速示例:

if( useD3D )
    IRenderer::instance = new D3DRenderer
else
    IRenderer::instance = new OpenGLRenderer