C++设计模式之动态创建

Abstract:
1,基本元素:工厂模式、函数指针和函数指针映射、链表、宏、静态全局变量控件、(虚函数)多态
2,链表地址追踪实验;
3,MFC动态创建原理演示;
4,自定义动态创建示例;

一、简述
动态创建(Dynamic Creation)是MFC六大核心机制之一。它的本质就是在运行时根据“类的某些信息”(如类名——字符串)创建对应的类对象,且客户代码(类对象的创建之处)无需包含待创建的类的头文件。或者说,客户代码在不知道待创建类的情况下,仅根据 “类的某些信息”(如类名)即可在运行时创建该类的对象。下面将举两个实际应用的例子来体会动态创建的作用和精妙。(参考侯俊杰的《深入浅出MFC》,本文是对该书学习应用的体会和心得)
1,存档和读档
假如要实现一个存档和读档的功能。其中,存档是将运行时某些类对象的信息存储到文件中,而读档则是在运行时读取文件,并根据读取的信息(字符串)来创建与原来一致的类对象。现有ObjectA1、 ObjectA2、 ObjectA3、 ObjectB1、 ObjectB2、 ObjectB3、 ObjectC1、 ObjectC2和 ObjectC3,分属类ClassA、 ClassB和 ClassC。存档的时候只需要保存类对象对应的类名和数据成员的值,如 ObjectA1保存为“ClassA"+相应数据成员的值。读档的时候,首先要根据读到的类名来创建类对象,然后在给该类对象进行各项赋值(恢复其数据成员值)。其中,根据类名(字符串)来创建类对象,一般的实现是:在客户代码中进行字符串比较,然后创建符合条件的类对象。这种方法有很多缺点:1)读档和存档的类名要一致,若要修改两处都要修改;2)读档的时候,需要设计多个if/else分支,如果后续要增加类,则修改重新修改代码(客户代码要修改),增加新分支的判断;3)客户代码(读档)需要包含各个待创建的类的头文件,如果新增类,又要修改客户代码,包含更多头文件;
2,测试项切换
假设有这么一个用于信号测试的软件工程,共计有N个测试项(N>10,且N可变),用类CTestItem的子类表示,另有4个图形窗口,用类Plot表示。每个图像窗口每次显示一个测试项的信息(可以是曲线图或数据表),这些图像窗口和测试项都托管于主窗口(mainwindow)。在运行时,四个图像窗口最多只能显示4个测试项的信息,即mainwindow中嵌套了四个对应的CTestItem和Plot类对象。如果要显示其他测试项的信息,则需要在运行时进行类 CTestItem的不同子类的delete和new,然后在重新与Plot绑定。一般的做法是:向mainwindow对象传入待创建的CTestItem子类的类名,然后在mainwindow中进行”字符串比较“,设计多个if/else分支,创建不同的 CTestItem子类对象。这样做的缺点是:1)要确保传入的类名与mainwindow中的字符串一致;2)如果测试项有增删和修改,需要修改 mainwindow中进行”字符串比较“部分的代码和if/else分支的代码;3)需要在mianwindow中包含全部的 CTestItem子类的头文件。

问题已经提出,如何解决,这就需要用到”动态创建“的设计模式。以上两个案例的一般设计模式的缺点,在”动态创建“设计模式中都可以被解决。总结”动态创建“设计模式的优势如下:
1)客户代码无需包含各个待创建类对象的头文件,仅仅只要包含它们的虚基类的头文件即可;
2)客户代码中没有if/else分支和”字符串判断“,仅仅只要在接口中增加一个字符串参数,接收传入的类名,再将类名传递给工厂函数即可,代码简洁;
3)客户代码(创建类对象部分的代码)写好后,后续有新增类,无需修改客户代码;
4)新增类类型时,也不需要修改虚基类,仅仅只要在新增类中添加”动态创建“相关的宏即可;
”动态创建“设计模式为什么会有如此神奇?下面让我们来它的实现原理。

二、”动态创建“的实现原理
”动态创建“设计模式综合运用了这样几种技术:工厂模式(工厂函数,factory function)、函数指针与字符串的封装(函数指针映射)、链表、类的静态成员和静态函数(的全局作用域)、(虚函数)多态和宏。
1,工厂模式
”动态创建“设计模式中,类对象的创建都不是直接在客户代码中new出来的,而是通过调用工厂函数获得类对象。在动态创建的实现宏中,有如下代码:
    CTestItem * class_name::CreateObject(QWidget** ppWidget) 
        { return new class_name(ppWidget); } 
这个CreateObject()函数就是工厂函数。它创建一个子类对象,并返回一个指向该子类对象的基类指针,可以是虚基类。

2,函数指针映射
”动态创建“设计模式中,要将上述工厂函数的函数地址
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值