概述
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
00003.七大软件架构设计原则
- 前言
- 一、开闭原则
- 1.开闭原则的定义
- 2. 使用开闭原则解决实际问题
- 二、依赖倒置原则
- 1.依赖倒置原则的定义
- 2.使用依赖倒置原则解决实际问题
- 总结
前言
提示:这里可以添加本文要记录的大概内容:
例如:软件设计的七大架构设计,指导着软件设计的。
提示:以下是本篇文章正文内容,下面案例可供参考
一、开闭原则
1.开闭原则的定义
- 开闭原则(Open-Closed Principle, OCP)指一个软件实体如类,模块和函数应对扩展开放,对修改封闭,即该原则是对软件扩展和修改的一项原则,强调的是用抽象构建框架,用实现扩展细节,目的是提高软件的可复用性和可维护性。该原则可以建立稳定灵活的系统,如:版本更新,我们尽可能不修改源码,但是可以增加新功能。
- 实现开闭原则的核心思想就是面向抽象的编程。
2. 使用开闭原则解决实际问题
- 如设计一个学生管理系统,该学生管理系统包括对学生信息的存储,包括学生的年龄,性别,学历等。案例代码如下
class CStudentOptImp {
public:
virtual std::string GetName() = 0;
virtual int GetAge() = 0;
virtual std::string GetEducation() = 0;
};
class CStudent: public CStudentOptImp {
public:
CStudent(const std::string name, const int age, const std::string education) :m_sName(name), m_iAge(age), m_sEducation(education) {
}
virtual std::string GetName() {
return m_sName;
}
virtual int GetAge() {
return m_iAge;
}
virtual std::string GetEducation() {
return m_sEducation;
}
private:
std::string m_sName;
int m_iAge;
std::string m_sEducation;
};
class CStudentRecord :public CStudent {
public:
CStudentRecord(const std::string name, const int age, const std::string education, const int record) :CStudent(name, age, education), m_iRecord(record) {
}
int GetRecord() {
return m_iRecord;
}
private:
int m_iRecord;
};
void test01() {
std::shared_ptr<CStudent> p = std::shared_ptr<CStudent>(new CStudent("venus", 26, "硕士"));
std::cout << "姓名:" << p->GetName() << "t年龄:" << p->GetAge() << "t学历:" << p->GetEducation() << std::endl;
}
int main() {
test01();
return 0;
}
- 案例结果如下:
- 而如果此时增加了学生的成绩信息,就需要修改Student类,这项操作是很不稳定的,因为系统中别的类可能调用了该类,修改可能会导致别的功能出现错误或者bug,因而软件开发过程中需要遵循开闭原则,只能通过添加代码达到目的,而不能通过修改代码。如下,此时可以通过继承,增加代码达到目的。详细代码如下:
class CStudentOptImp {
public:
virtual std::string GetName() = 0;
virtual int GetAge() = 0;
virtual std::string GetEducation() = 0;
};
class CStudent: public CStudentOptImp {
public:
CStudent(const std::string name, const int age, const std::string education) :m_sName(name), m_iAge(age), m_sEducation(education) {
}
virtual std::string GetName() {
return m_sName;
}
virtual int GetAge() {
return m_iAge;
}
virtual std::string GetEducation() {
return m_sEducation;
}
private:
std::string m_sName;
int m_iAge;
std::string m_sEducation;
};
class CStudentRecord :public CStudent {
public:
CStudentRecord(const std::string name, const int age, const std::string education, const int record) :CStudent(name, age, education), m_iRecord(record) {
}
int GetRecord() {
return m_iRecord;
}
private:
int m_iRecord;
};
void test01() {
std::shared_ptr<CStudent> p = std::shared_ptr<CStudent>(new CStudent("venus", 26, "硕士"));
std::cout << "姓名:" << p->GetName() << "t年龄:" << p->GetAge() << "t学历:" << p->GetEducation() << std::endl;
}
void test02() {
std::shared_ptr<CStudentRecord> p = std::shared_ptr<CStudentRecord>(new CStudentRecord("venus", 26, "硕士", 100));
std::cout << "姓名:" << p->GetName() << "t年龄:" << p->GetAge() << "t学历:" << p->GetEducation() << "t成绩:" << p->GetRecord() << std::endl;
}
int main() {
//test01();
test02();
return 0;
}
- 案例结果如下:
- 最后回顾以下整个开闭原则的类图关系:
二、依赖倒置原则
1.依赖倒置原则的定义
- 依赖倒置原则(Dependence Inversion Principle,DIP)指设计代码结构时,高层模块不应该依赖底层模块。二者都应该依赖其抽象。抽象不应该依赖细节,细节应该依赖抽象。 通过依赖倒置可以减低类与类之间的耦合性,提高系统的稳定性,提高代码的可读性和可维护性。
2.使用依赖倒置原则解决实际问题
- 我们以张三丰为例,建立张三丰类如下。
#include <iostream>
class Zhangshanfen {
public:
void StudyTaiChiSword() {
std::cout << "学习了太极剑" << std::endl;
}
void StudyTaiJiBoxing() {
std::cout << "学习了太极拳" << std::endl;
}
};
int test01() {
std::shared_ptr<Zhangshanfen> p = std::shared_ptr<Zhangshanfen>(new Zhangshanfen);
p->StudyTaiChiSword();
p->StudyTaiJiBoxing();
return 0;
}
int main() {
test01();
return 0;
}
- 上面代码效果:
- 上面代码,如果当张三丰想学习武当剑法的时候,需要重写该段代码,这样程序就会变得不稳定。因此可以考虑将各种武功抽象出来,形成一个抽象类。代码如下:
#include <iostream>
class Kungfu {
public:
virtual void Study() = 0;
};
class TaiJiSword: public Kungfu {
public:
virtual void Study() override {
std::cout << "学习太极剑" << std::endl;
}
};
class TaiJiBoxing :public Kungfu {
public:
virtual void Study() override {
std::cout << "学习太极拳" << std::endl;
}
};
class WudangSwordTechnique :public Kungfu {
public:
virtual void Study() override {
std::cout << "学习武当剑法" << std::endl;
}
};
class Zhangshanfen {
public:
void Study(Kungfu* kungfu) {
kungfu->Study();
}
};
int test01() {
Zhangshanfen* p = new Zhangshanfen();
p->Study(new TaiJiSword);
p->Study(new TaiJiBoxing);
p->Study(new WudangSwordTechnique);
return 0;
}
int main() {
test01();
return 0;
}
- 该代码的演示效果如下:
- 这个时候不管张三丰想学什么新的武功,对于新的武功,只需要新建一个类,通过传参的方式告诉张三丰,而不需要修改底层代码。实际上,这是一种大家非常熟悉的方式, 叫做依赖注入。此外注入的方式还有构造器注入方式和Setter注入方式,下面来看构造器注入方式。
class Zhangshanfen {
public:
Zhangshanfen(Kungfu* kunfu) {
this->kunfu = kunfu;
}
void Study() {
this->kunfu->Study();
}
private:
Kungfu* kunfu;
};
- 测试代码如下
int test01() {
Zhangshanfen* p = new Zhangshanfen(new TaiJiSword);
p->Study();
return 0;
}
- 根据构造器注入方式,当调用时,每次都要创建实例,那么如果张三丰是全局单例,则只能使用Setter注入方式。代码如下:
class Zhangshanfen {
public:
void setter(Kungfu* kungfu) {
this->kungfu = kungfu;
}
void Study() {
this->kungfu->Study();
}
private:
Kungfu* kungfu;
};
- 测试端代码如下:
int test01() {
Zhangshanfen* p = new Zhangshanfen();
p->setter(new TaiJiBoxing);
p->Study();
return 0;
}
- 最终得到UML类图如下:
总结
提示:这里对文章进行总结:
例如:以上就是今天要讲的内容,本文仅仅简单介绍了pandas的使用,而pandas提供了大量能使我们快速便捷地处理数据的函数和方法。
最后
以上就是疯狂小天鹅为你收集整理的00003.七大软件架构设计原则前言一、开闭原则二、依赖倒置原则总结的全部内容,希望文章能够帮你解决00003.七大软件架构设计原则前言一、开闭原则二、依赖倒置原则总结所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
发表评论 取消回复