《more effective c++》条款26 限制类对象的个数
问题:
如何限制类对象的个数?比如1个,10个等等。
方法(1):
将类的构造函数定义为private,那么就无法实例化这个类了。但是如何创建1个对象出来?方法有2种:
1.声明一个友元函数,那么在友元函数中就可以调用构造函数了,创建对象时使用static限制,那么就保证只有一个对象了。类似的定义如下:
class Printer
{
public:
friend Printer& thePrinter();
private:
Printer();
Printer(const Printer& rhs);
};
Printer& thePrinter()
{
static Printer p;
return p;
}
2.定义一个静态成员函数来代替上面的友元函数也是可以达到同样效果的,就是调用时麻烦了些,需要加上类名才能调用函数,但是这也是可以解决的,将类定义在一个命名空间(namespace)中,再using该命名空间即可直接使用函数名来调用了(具体去看如何定义命名空间)。使用命名空间还可以防止出现名字冲突问题,而且将对象声明在函数中的好处是,只有当调用该函数时,对象才会被创建。注意:尽量不要在内联函数中创建静态对象,可能产生多个副本。
class Printer
{
public:
static Printer& thePrinter();//注意这里
private:
Printer();
Printer(const Printer& rhs);
};
Printer& thePrinter()
{
static Printer p;
return p;
}
方法(2):
在类中定义一个静态计数器,通过计数器来限制实例对象的个数,一旦创建超过限制的个数就抛出异常。这貌似更加好用。
如果单例类是作为基类被继承,那么派生类对象中的基类部分也会被统计进去了,比如彩色打印机继承自打印机,而现在有1台打印机,2台彩色打印机,计数器就是3了。显然不符合我们的要求,我们可以通过private构造函数,那么单例类就无法被继承了。
允许对象来去自由
通常情况下,我们希望可以这样:
create Printer1;
use Printer1;
destroy Printer1; create Printer2;
use Printer2;
destroy Printer2;
但是方法(1)并不能支持。但是结合计数器就可以实现了。具体看书 P105中的代码例子。
一个用于对象计数的基类
如果需要多个具体类怎么办?难道一个个去写去实现?其实可以用模板类作为基类来完成这个功能,使用前将设置一下实例个数就可以使用了,具体看书 P107。
《more effective c++》条款26 限制类对象的个数的更多相关文章
- Effective C++ 条款13/14 以对象管理资源 || 在资源管理类中小心拷贝行为
三.资源管理 资源就是一旦你使用了它,将来不用的时候必须归还系统.C++中最常用的资源就是动态内存分配.其实,资源还有 文件描述符.互斥器.图形界面中的字形.画刷.数据库连接.socket ...
- Effective C++ 条款26
尽可能延后变量定义式的出现时间 我们知道定义一个对象的时候有一个不争的事实,那就是分配内存.假设是我们自己定义的对象.程序运行过程中会调用类的构造函数和析构函数. 我们打个例如,假设天下雨了,你带把雨 ...
- Effective C++ -----条款13:以对象管理资源
为防止资源泄漏,请使用RAII(Resource Acquisiton Is Initialization) 对象,它们在构造函数中获得资源并在析构函数中释放资源. 两个常被使用的RAII class ...
- Effective C++ 条款12:复制对象时勿忘其每一个成分
void logCall(const std::string& funcName); class Customer { public: ... Customer (const Customer ...
- Effective C++ 条款04:确定对象被使用前已经先被初始化
规则一 永远在使用对象之前将它初始化 int x = 0; const char* text = "A C-style string"; double d; std:: cin & ...
- Effective C++ -----条款26:尽可能延后变量定义式的出现时间
尽可能延后变量定义式的出现.这样做可增加程序的清晰度并改善程序效率.
- effective c++ 条款26 postpone variable definition as long as possible
因为构造和析构函数有开销,所以也许前面定义了,还没用函数就退出了. 所以比较好的方法是用到了才定义.
- Effective Objective-C 2.0 — 第14条:理解“类对象“的用意
每个实例都有一个指向Class 对象的指针,用以表明其类型,而这些 Class 对象则构成了类的继承体系. 如果对象类型无法在编译期确定,那么就应该使用类型信息查询方法来探知. 尽量使用类型信息查询方 ...
- MoreEffectiveC++Item35 条款26: 限制某个class所能产生的对象个数
一 允许零个或一个对象 我们知道每当即将产生一个对象,我们有一个constructor被调用,那么我们现在想组织某个对象的产生,最简单的方法就是将其构造函数声明成private(这样做同事防止了这个类 ...
随机推荐
- linux 命令大全(转)
系统信息 arch 显示机器的处理器架构(1) uname -m 显示机器的处理器架构(2) uname -r 显示正在使用的内核版本 dmidecode -q 显示硬件系统部件 - (SMBIOS ...
- 用于主题检测的临时日志(452a49c2-4455-430f-a1cc-bbcd2d1944dd - 3bfe001a-32de-4114-a6b4-4005b770f6d7)
这是一个未删除的临时日志.请手动删除它.(95c74eab-5822-4f4b-b0e5-009feb9cae8d - 3bfe001a-32de-4114-a6b4-4005b770f6d7)
- 检索 COM 类工厂中 CLSID 为 {000209FF-0000-0000-C000-000000000046} 的组件失败,原因是出现以下错误: 8000401a 因为配置标识不正确,系统无法开始服务器进程。请检查用户名和密码。 (异常来自 HRESULT:0x8000401A)。
检索 COM 类工厂中 CLSID 为 {000209FF-0000-0000-C000-000000000046} 的组件失败,原因是出现以下错误: 8000401a 因为配置标识不正确,系统无法开 ...
- X61的intel wireless 3945abg 不再掉线了
X61本的3945ABG无线网卡总是用一段时间就掉一次线(大约一个小时不到),换过两个路由器都这毛病. 今天有空,查了下,把网卡的“节约电源”去掉了,照样掉. 升级了驱动,掉的更勤了. 调整无线通道, ...
- 提升WordPress站点速度的八个建议
WordPress是一个很棒的开源程序,几乎我认识的站长朋友当中,粗略估算有80%使用Wordpress.但很棒不等于完美,就在我所认识的这些朋友中,几乎所有人都会抱怨Wordpress太臃肿,运行效 ...
- 关于JavaScript是否会阻塞图片加载
<?php //1.js.php sleep(5); file_put_contents("tmp.txt", __FILE__.'->'.__LINE__.' -&g ...
- 设置groupBox背景透明
步骤:属性-BackColor-WEB面板-Transparent
- 神奇的NOIP模拟赛 T2 LGTB 学分块
LGTB 学分块 LGTB 最近在学分块,但是他太菜了,分的块数量太多他就混乱了,所以只能分成3 块今天他得到了一个数组,他突然也想把它分块,他想知道,把这个数组分成3 块,块可以为空.假设3 块各自 ...
- URL动态赋值
url动态赋值: 指的是url中包含{selector},即花括号括起来的jQuery选择器,当提交该url时,框架会自动将selector对应元素的值替换到花括号所占区域. (感觉实现了一点类似el ...
- Android studio 环境搭建
环境变量: CLASSPATH:.;%JAVA_HOME%\lib;%JAVA_HOME%\lib\tools.jar;%JAVA_HOME%\lib\dt.jar JAVA_HOME:F:\Prog ...