文章目录
前言
学习设计模式,需要了解面向对象思想。利用面向对象思想的特性,能够帮助我们设计出优秀的程序。
面向过程思想
特点
- 关注点:正在发生的过程
- 事情的发生按照一定的“逻辑时间顺序”
- 符合多数人思考、计算机处理问题的逻辑
示例(C++语言描述)
#include <iostream>
using namespace std;
int main()
{
	//定义并初始化变量
    int num1 = 1;	//操作数1
    char oper = '+';	//计算符
    int num2 = 2;	//操作数2
    int result = 0;	//计算结果
	//判定并计算
    switch (oper)
    {
    case '+':
        result = num1 + num2;
        break;
    case '-':
        result = num1 - num2;
        break;
    default:
        break;
    }
    cout << result << endl;	//输出计算结果
    return 0;
}
程序先定义并初始化变量,然后进行判断计算,最后输出结果。程序的执行“从上至下”(按照语句顺序),“从过去到未来”(按照时间顺序)经历一定的过程。
缺点
- 维护性差
- 复用性差
- 扩展性差
- 灵活性差
优秀程序设计的四个特性
在实际业务、服务开发中,需求变化,程序就要修改。优秀程序设计旨在用更短的时间、变动更少的代码、按一定设计步骤有序无差错地完成任务。
- 维护性:只修改相关代码/功能,而不影响其他代码/功能
- 复用性:代码/功能可重复使用
- 扩展性:能在原有代码/功能基础上,增添新的代码/功能
- 灵活性:代码/功能适用于多种场景
面向对象思想
关注点:正在受影响的对象
 三大特性:封装,继承,多态
封装
目的
- 拆分逻辑
- 降低耦合度
- 隐藏实现细节
- …
示例(C++语言描述)
#include <iostream>
using namespace std;
//计算类
class Operation	
{
public:
    int num1;	//操作数1
    char oper;	//计算符
    int num2;	//操作数2
    int result;	//计算结果
	//计算方式
    void calculate()
    {
        switch (oper)
        {
        case '+':
            result = num1 + num2;
            break;
        case '-':
            result = num1 - num2;
            break;
        default:
            break;
        }
    }
};
int main()
{
	//创建并初始化计算类的对象
    Operation operation;	
    operation.num1 = 1;
    operation.oper = '+';
    operation.num2 = 2;
    
    operation.calculate();	//计算
    cout << operation.result << endl;	//输出计算结果
    return 0;
}
程序定义了一个计算类,将”操作数、操作符、计算结果和计算方式”逻辑相似且共同实现一种功能的“实体”封装;在主函数中将计算的业务逻辑和输出显示的界面的代码逻辑拆分,修改代码可选择只修改其中一部分而不影响另一部分,耦合度降低;对主函数而言,计算类的实现细节是隐藏的,主函数只需知道如何调用,可以将计算类复用在其他位置。
继承和多态
目的
- 拆分逻辑
- 降低耦合度
- …
当需要修改计算类时,仍然存在耦合度高的问题。例如想为其增添“乘法计算”功能,则需在“calculate()”函数的“switch”语句中添加代码,可能会错误修改“加法、减法计算”功能的代码。
示例(C++语言描述)
#include <iostream>
using namespace std;
//计算类
class Operation
{
public:
    int num1;   //操作数1
    char oper;  //计算符
    int num2;   //操作数2
    int result; //计算结果
    virtual void calculate() = 0; //纯虚函数
};
//计算加法类
class Operation_add : public Operation //继承
{
    void calculate() //重载  多态
    {
        result = num1 + num2;
    }
};
//计算减法类
class Operation_sub : public Operation
{
    void calculate()
    {
        result = num1 - num2;
    }
};
//计算乘法类
class Operation_mul : public Operation
{
    void calculate()
    {
        result = num1 * num2;
    }
};
/**
 * 程序设计思路:依据给定的计算符,创建计算类相应的子类对象,调用子类的方法计算
 * 使用简单工厂模式
 */
//计算工厂类
class Operation_factory
{
public:
    static Operation *create_operation(char oper) //静态函数
    {
        Operation *operation = NULL; //指向计算类的指针
        //依据给定的计算符,创建计算类相应的子类
        switch (oper)
        {
        case '+':
            operation = new Operation_add();
            break;
        case '-':
            operation = new Operation_sub();
            break;
        case '*':
            operation = new Operation_mul();
            break;
        default:
            break;
        }
        return operation;	//返回相应的计算子类对象
    }
};
int main()
{
	//依据给定的计算符,创建计算类相应的子类对象并初始化
    Operation *operation = Operation_factory::create_operation('+');	
    //静态函数属于类而不是对象,由类直接调用
    operation->num1 = 1;
    operation->num2 = 2;
    
    operation->calculate();	//计算
    cout << operation->result << endl;	//输出计算结果
    return 0;
}
通过继承,将“计算”的各个“子功能”逻辑拆分,每个功能单独成一“类”,耦合度降低;通过多态,将函数重载以实现不同的计算。当再想增加一个“除法计算”功能时,只需增加一个计算除法子类,并在计算工厂类的“switch”语句中增加一个创建计算除法子类对象的分支,而不会“触碰”/误修改到“加、减和乘法计算”功能的代码,提高了程序的维护性。
总结
- 面向过程的关注点:正在发生的过程
- 优秀程序设计的四大特性:维护性,复用性,扩展性,灵活性
- 面向对象的关注点:正在受影响的对象
- 三大特性:封装,继承,多态
作者的话
- 文章内容基于读者有一定程序设计基础,了解面向过程、对象思想等一定知识,主要目的是对知识的串讲、延拓,详细概念理解请参阅其他资料
- 文章内容示例简单,思想优越性的体现可能不理想。当拓展到大型业务、服务和程序时,务须具备高效的设计思想、使用良好的设计模式编程
- 文章在描述时有疑惑的地方,请留言,必会一一耐心讨论、解答
- 文章在认识上有错误的地方, 敬请批评指正
- 望读者们都能有所收获
参考资料
《大话设计模式》作者:程杰









