C++简单工厂模式详解

news2024/11/20 18:25:39

C++简单工厂模式详解

  • 1.问题引入
  • 2.编写代码思路的迭代
    • 2.1 main函数主体内编写全部代码
    • 2.2 修改上述问题后的main函数代码
    • 2.3 引入面向对象后的代码
    • 2.4 加上继承和多态后的代码
  • 3.C++简单工厂代码
  • 4.总结
    • 4.1 简单工厂模式适用场景
    • 4.2收获

1.问题引入

编写一个计算器程序代码,可使用任意一种面向对象语言编写。

2.编写代码思路的迭代

2.1 main函数主体内编写全部代码

在main函数主题写好了全部逻辑。包括两个运算数字的获取,中间运算符号的获取,通过对符号的if分支判断选取运算符参与运算数字的运算。这个时候出现的问题有:1.命名不规范。很多变量名都是A,B,C,不能通过名字知晓含义。2.if分支判断做了三次无用功,在这里可以选用switch。3.除法没有考虑除0判断,程序的健壮性不够。之后进行了第一次修改。

2.2 修改上述问题后的main函数代码

修改上诉问题后代码是没问题的,但是问题是不符合出题人心意。当前代码由于全部都在main函数里面,程序不容易维护,不容易拓展,不容易复用,不够灵活。
软件可维护性指的是维护人员对该软件进行维护的难易程度,具体包括理解、改正、改动和改进该软件的难易程度。
软件的可扩展性表现为基础设置不需要经常变更,应用之间较少依赖或耦合,可以对需求变更快速响应。
软件复用是使用已有的软件组件去实现或更新软件系统的过程。
软件开发中的灵活性通常是指管理方法和开发方法的灵活性,更细微的范围内则是指编码的灵活性。如果在解决某一问题时具备了多种可选择的方法,则可以认为开发过程拥有灵活性。
故接下来进行第二次修改。

2.3 引入面向对象后的代码

代码分为两部分,一部分是关于operation类的编写,包含了两个成员变量及计算的成员方法。另一个部分是主函数的编写。这样的好处是实现了业务和界面的分离。缺点是这里只用了封装,没有用到面向对象中的继承和多态。假如要新加一个开根号的运算(假设这里它只有加减乘除的运算),那么需要拿到所有方法代码再进行修改,但其实感觉上而言都是奇怪的操作,因为只想新加一个功能却需要拿到所有功能的代码才能进行添加。其实归根结底就是耦合度太高。
耦合度是某模块(类)与其它模块(类)之间的关联、感知和依赖的程度,是衡量代码独立性的一个指标,也是软件工程设计及编码质量评价的一个标准。
故接下来进行第三次修改。

2.4 加上继承和多态后的代码

在上一步,operation是作为主类,但是由于耦合度太高,所以做进一步耦合度的降低,采用继承和多态。所以有关于计算的四个类operationAdd、operationSub、operationMul、operationDiv继承operation,并且在operation中有虚方法getResult,子类里面都对该方法进行重写,从而实现多态。
那么其实就剩一个问题:就是实例化对象,比如增加开根号运算,那么我们应该考虑用一个类单独去制造出对象,这就是简单工厂模式。

3.C++简单工厂代码

//simpleFactory.h
#ifndef _SimpleFactory_H_
#define _SimpleFactory_H_

#include <iostream>
#include <exception>
#include <string>

using namespace std;

class Operation{
    protected:
        double _numberA = 0;
        double _numberB = 0;
    public:
        Operation(){}
        Operation(double a, double b){
            _numberA = a;
            _numberB = b;
        }
        Operation &operator=(Operation &p){
            _numberA = p.getNumberA();
            _numberB = p.getNumberB();
        }
        double getNumberA(){
            return _numberA;
        }
        void setNumberA(double value){
            _numberA = value;
        }
        double getNumberB(){
            return _numberB;
        }
        void setNumberB(double value){
            _numberB = value;
        }
        virtual double GetResult(){
            return 0;
        }
};
class OperationAdd:public Operation{
    double GetResult(){
        double result = 0;
        result = _numberA + _numberB;
        return result;
    }
};
class OperationSub:public Operation{
    double GetResult(){
        double result = 0;
        result = _numberA - _numberB;
        return result;
    }
};
class OperationMul:public Operation{
    double GetResult(){
        double result = 0;
        result = _numberA * _numberB;
        return result;
    }
};
class OperationDiv:public Operation{
    double GetResult(){
        double result = 0;
        try{
            result = _numberA / _numberB;
        }catch(exception &){
            cout << "发生除0异常" << endl;
        }
        return result;
    }
};
class OperationFactory{
    public:
        static Operation* createOperation(char operate){
            Operation* oper;
            switch (operate){
                case '+':
                    oper = new OperationAdd();
                    break;
                case '-':
                    oper = new OperationSub();
                    break;
                case '*':
                    oper = new OperationMul();
                    break;
                case '/':
                    oper = new OperationDiv();
                    break;
            }
            return oper;
        }
};
#endif //_SimpleFactory_H_
//simpleFactory.cpp
#include "simpleFactory.h"

int main(){
    Operation* oper;
    oper = OperationFactory::createOperation('+');
    oper->setNumberA(1);
    oper->setNumberB(2);
    double result = oper->GetResult();
    std::cout << "Result: " << result << std::endl;
    return 0;
}
//CSDN@Credic1017

4.总结

4.1 简单工厂模式适用场景

在这里插入图片描述

可以发现,简单工厂类是制造运算类的对象的,并且只需要传递关键参数给简单工厂类的方法(通常为静态方法),就可以创造出相应的对象出来。
故简单工厂适用于工厂类负责创建的对象较少的场景,且客户端只需要传入工厂类的参数,对于如何创建对象不需要关心。

4.2收获

1.可以通过封装、继承、多态把程序的耦合度降低。
2.可以通过设计模式使程序变得更加灵活,易于修改,并且易于复用。
3.简单工厂模式适用创建对象少的情况,需要传参来指定需要的对象(产品)。

参考:《大话设计模式》

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/10704.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

论文笔记:Region Representation Learning via Mobility Flow

2017 CIKM 1 摘要和介绍 使用出租车出行数据学习区域向量表征 同时考虑时间动态和多跳位置转换——>通过flow graph和spatial graph学习表征出租车交通流可以作为区域相似度的一种 A区域和B区域之间流量大 ——>A和B的特征更相关——>用一个/很相似的vector来表征他…

如何实现基于场景的接口自动化测试用例?来看看大佬的方案

自动化本身是为了提高工作效率&#xff0c;不论选择何种框架&#xff0c;何种开发语言&#xff0c;我们最终想实现的效果&#xff0c;就是让大家用最少的代码&#xff0c;最小的投入&#xff0c;完成自动化测试的工作。 基于这个想法&#xff0c;我们的接口自动化测试思路如下…

R语言七天入门教程七:项目实战

R语言七天入门教程七&#xff1a;项目实战 在完成之前R语言基础知识的学习后&#xff0c;今天的内容是项目实战&#xff0c;通过完成一些小项目来巩固知识。 一、矩阵运算计算器&#xff08;变量与运算符练习&#xff09; 1、问题描述 给定矩阵A和B&#xff0c;计算矩阵相加…

MySql常用内置函数详解

目录日期函数--了解***字符串函数--重要数学函数--了解其他函数--了解MySql为我们提供了一些内主函数&#xff0c;方便我们对特定数据进行相关操作&#xff01; 注意:都是配合select使用哦&#xff0c;个人理解SQL的select相当于C中的printf; 日期函数–了解 一般用于insert in…

C++ 主函数几种语法

Cmain函数的两种写法 1&#xff0c;返回值为int&#xff0c;且main不带参数 #include<iostream> using namespace std; int main() { cout << "Hello C \n" << endl; system("pause"); return 1;//函数返回值取值范围0到255&#xf…

深入了解 JavaScript 语法错误以及如何防止它们

最近&#xff0c;在 Leader 的建议下&#xff0c;去看了看 emotion 和 storybook 的相关文档。学习过后&#xff0c;小有收获。因此&#xff0c;这次将以我自己的视角带你们体验一下 storybook&#xff0c;也算是对我自己学习过程中的一个 review。 何为 storybook 什么是 st…

第2关:伪分布式体验及分布式安装配置

服务器leader选举 为进一步了解ZooKeeper的leader选举过程&#xff0c;本节实训利用服务器的关闭启动&#xff0c;观察服务器的leader产生过程。利用以下命令查看当前服务器节点的状态(/xxx为安装目录)&#xff1a; ./xxx/bin/zkServer.sh status 当仅启动1个服务器节点&…

进博会期间,多地政府领导密集考察深兰科技

从11月初开始&#xff0c;借第五届中国国际进口博览会在上海举办的契机&#xff0c;来自全国各地的地级、县级市的各级领导纷纷来到上海&#xff0c;深入到各个行业领域的国企、央企、民企和跨国企业中走访调研&#xff0c;寻求技术合作&#xff0c;洽谈招商引资。 期间仅1日至…

流体力学基础——简介

流体定义&#xff1a;无规则的运动&#xff0c;流体&#xff1b;流体在静止时内部不能产生剪切力&#xff0c;流动产生的剪切力叫做粘力流体特点&#xff1a; 1、力与变形的关系不同&#xff1b;固体&#xff0c;应力正比于应变&#xff0c;静力学为主&#xff1b;流体&#xf…

DeepLearn关于数组和数的操作

本篇文章纯属作为自己的笔记&#xff0c;因为每次写程序都忘记下面的内容&#xff0c;找起来又很浪费时间&#xff0c;所有就索性一次性都整理下来&#xff0c;后续又不新的不会的内弄也会及时更新到文章当中&#xff0c;方便以后查阅。 DeepLearn关于数组和数的操作Python标准…

【详解】BIO、AIO、NIO Netty 知识点和工作原理

Netty框架 基础 三大网络编程 BIO 同步阻塞:服务器实现模式一个连接一个线程,既客户端有连接请求时,服务器就需要启动一个线程进行处理,如果这个连接不任何事情会造成不必要的线程线程开销 适用场景&#xff1a; 连接数目比较小且固定的架构&#xff0c;这种方式对服务器资源…

Android企业微信分享到小程序

1.官方文档Android应用 - 接口文档 - 企业微信开发者中心https://developer.work.weixin.qq.com/document/path/91196 2.创建应用 登录企业微信管理后台&#xff0c;选择企业应用&#xff0c;选择“企业微信授权登录”&#xff0c;在设置界面填写Android的 App的签名&包名…

[附源码]java毕业设计基于技术的新电商助农平台

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

HTTP 消息头

title: HTTP 消息头 date: 2022-11-16 14:36 tags: [HTTP,X-Real-IP,Host,X-Forwarded-For,Nginx] 文章目录〇、问题一、前言二、什么是消息头&#xff1f;三、Host四、X-Real-IP五、X-Forwarded-For参考更新〇、问题 什么是HTTP Headers&#xff1f;作用是什么&#xff1f; …

qemu-system-aarch64使用记录

qemu-system-aarch64 使用记录下载安装qemu查看是否支持KVM运行qemu-M内核启动问题内核编译下载安装qemu #!/bin/bashsudo apt update > /dev/null sudo apt upgrade > /dev/null sudo apt-get install -y make gcc g git > /dev/nullcd sudo apt-get install -y r…

一起来庆祝属于GISer的节日GIS DAY

概述 作为一名GISer的你&#xff0c;有没有想过其实我们GISer也有自己的节日&#xff1f;这个节日便是GIS DAY&#xff0c;今年的GIS DAY恰在今天&#xff08;2022年11月16日&#xff09;。究竟什么是GIS DAY&#xff1f;这里为大家介绍一下这个节日。 什么是GIS DAY GIS DA…

Python学习----异常、模块、安装第三方包

异常 异常的含义就不用解释了 打开一个不存在的文件&#xff1a; 异常的捕获 语法&#xff1a; 捕获所有异常 try:可能发生错误的代码 except:发生错误之后执行的代码try:可能发生错误的代码 except Exception as e:发生错误之后执行的代码两种写法都行 捕获指定异常&…

【maptplotlib大全图】一段代码洞查matplotlib图片真谛

此文通过给大家设计一个全面的代码&#xff0c;帮助大家了解matplotlib库画图的全貌 代码解读&#xff0c;略。 图示解读&#xff1a; 对照上图序号和下面序号看代码解释&#xff1a; 1.应用风格使用代码&#xff1a;plt.style.use(sty) 2.文本注释 plt.annotate(‘maximum…

QSS(Qt样式表)概念

Qt样式表是一个可以自定义部件外观的十分强大的机制&#xff0c;除了QStyle更改的样式&#xff0c;其他的都可以由QSS修改。由于受到Html的CSS启发&#xff0c;所以叫QSS。 代码添加样式表ui界面上添加样式表代码添加样式表&#xff1a; setStyleSheet&#xff08;&#xff09…

Beacon帧

一、简介 Beacon帧是802.11中一个周期性的帧&#xff0c;每隔一段时间就会向外界发出一个Beacon(信标)信号用来宣布自己802.11网络的存在。Beacon周期调高&#xff0c;对应睡眠周期拉长&#xff0c;故节能&#xff08;即越来休息100ms再起来发一个包&#xff0c;现在休息200ms…