C++ 如何强制单例类使用样式
假设我们有一个singleton类,其中实例函数(返回该类的singleton实例的函数)被重载。一个版本接受一些参数并在类构造函数中初始化对象,另一个版本不接受任何参数C++ 如何强制单例类使用样式,c++,oop,design-patterns,singleton,C++,Oop,Design Patterns,Singleton,假设我们有一个singleton类,其中实例函数(返回该类的singleton实例的函数)被重载。一个版本接受一些参数并在类构造函数中初始化对象,另一个版本不接受任何参数 1. myClass::Instance ( int x, int y ); 2. myClass::Instance ( ); 我们想要实现的是,类的用户应该总是先调用(1),然后再调用(2)。不应允许用户首次调用(2),并且一旦调用(1),就不允许再调用(1) 是否可以在不将检查空指针的负担放在类的用户身上的
1. myClass::Instance ( int x, int y );
2. myClass::Instance ( );
我们想要实现的是,类的用户应该总是先调用(1),然后再调用(2)。不应允许用户首次调用(2),并且一旦调用(1),就不允许再调用(1)
是否可以在不将检查空指针的负担放在类的用户身上的情况下实现这一点?在1中。
如果实例已经存在,则抛出异常(例如std::logic_error)。
如果没有,则使用提供的参数构造实例并返回它
在2。
如果实例还不存在,则抛出一个异常(例如std::logic\u error)。然后返回它。问题是编译器不可能在编译时仲裁这个“第一次调用”概念(因为它编译特定的翻译单元,它无法洞察(1)是否可以从其他翻译单元调用),因此您必须:
- 设计为在编译时限制对一个或两个重载的访问,和/或
- 检查运行时的有效使用情况,和/或
- 使您的代码更能容忍对(1)的多次调用,同时确保您获得所需的行为
- 您可以(1)通过将其设置为受保护的或私有的,同时向将调用它的特定代码授予友谊,从而使其更难访问,而将(2)设置为公共的,以便代码的其他部分继续方便地使用
- 您可以编写(1)的代码,以便在第一次之后它忽略任何参数并调用(2)
- 您可以在运行时使用断言来验证使用情况,这有望确保客户机代码在投入生产之前很久就符合您的条件
- 您可以(1)返回调用(2)所需的内容,例如客户端无法创建的类型的对象,但这本身并不能阻止再次调用(1)。所需的对象可能被传递给(2)的构造函数,或者(2)可能成为该对象上的函数
一次调用将确保函数仅在第一轮执行。显然,第一个问题应该是,没有Singleton可以吗?Singleton类仅确保实例在请求时可用。您的没有(是的,它是可用的,但您必须先调用此函数)。若创建实例的责任在于用户,那个么您根本并没有单例(这可能是一件坏事,也可能不是坏事)。@Matthieu M.不幸的是,在这种情况下需要单例。@n.M.传递给类的参数驻留在main()中;HWND和HINSTANCE(winapi)以及我们的singleton类没有访问这些参数的权限,因此保存参数并将实例返回给用户的singleton是有意义的?@StudentX:我同意这可能会变得单调乏味,但在许多情况下显式优于隐式。例如,如果要重新设计应用程序,使其具有两个窗口而不是一个窗口,该怎么办?然后,您将有两个
HWND
句柄,根据哪个处于活动状态,程序应绘制到其中一个。你不能用一个单身汉。。。然而,如果显式地传递句柄,这将是微不足道的。全局变量(如Singleton)隐藏数据流,并引入不可见的依赖项,这就是它们不好的原因(tm)。+1表示“设计为在编译时限制对一个或两个重载的访问”。