├── CMakeLists.txt ├── README.md ├── chain_of_responsibility_pattern ├── CMakeLists.txt └── main.cpp ├── command_pattern ├── CMakeLists.txt └── main.cpp ├── composite_pattern ├── CMakeLists.txt └── main.cpp ├── decorator_pattern ├── CMakeLists.txt └── main.cpp ├── facade_pattern ├── CMakeLists.txt └── main.cpp ├── factory_method_pattern ├── CMakeLists.txt └── main.cpp ├── flyweight_pattern ├── CMakeLists.txt └── main.cpp ├── interpreter_pattern ├── CMakeLists.txt └── main.cpp ├── iterator_pattern ├── CMakeLists.txt └── main.cpp ├── mediator_pattern ├── CMakeLists.txt └── main.cpp ├── memento_pattern ├── CMakeLists.txt └── main.cpp ├── observer_pattern ├── CMakeLists.txt └── main.cpp ├── prototype_pattern ├── CMakeLists.txt └── main.cpp ├── proxy_pattern ├── CMakeLists.txt └── main.cpp ├── simple_factory_pattern ├── CMakeLists.txt └── main.cpp ├── singleton_pattern ├── CMakeLists.txt └── main.cpp ├── state_pattern ├── CMakeLists.txt └── main.cpp ├── strategy_pattern ├── CMakeLists.txt └── main.cpp ├── template_method_pattern ├── CMakeLists.txt └── main.cpp └── visitor_pattern ├── CMakeLists.txt └── main.cpp /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(design_pattern) 4 | 5 | # 创建型 6 | add_subdirectory(${PROJECT_SOURCE_DIR}/factory_method_pattern) 7 | add_subdirectory(${PROJECT_SOURCE_DIR}/simple_factory_pattern) 8 | add_subdirectory(${PROJECT_SOURCE_DIR}/abstract_factory_pattern) 9 | add_subdirectory(${PROJECT_SOURCE_DIR}/singleton_pattern) 10 | add_subdirectory(${PROJECT_SOURCE_DIR}/builder_pattern) 11 | add_subdirectory(${PROJECT_SOURCE_DIR}/prototype_pattern) 12 | 13 | # 结构型 14 | add_subdirectory(${PROJECT_SOURCE_DIR}/adapter_pattern) 15 | add_subdirectory(${PROJECT_SOURCE_DIR}/bridge_pattern) 16 | add_subdirectory(${PROJECT_SOURCE_DIR}/composite_pattern) 17 | add_subdirectory(${PROJECT_SOURCE_DIR}/decorator_pattern) 18 | add_subdirectory(${PROJECT_SOURCE_DIR}/facade_pattern) 19 | add_subdirectory(${PROJECT_SOURCE_DIR}/flyweight_pattern) 20 | add_subdirectory(${PROJECT_SOURCE_DIR}/proxy_pattern) 21 | 22 | # 行为型 23 | add_subdirectory(${PROJECT_SOURCE_DIR}/command_pattern) 24 | add_subdirectory(${PROJECT_SOURCE_DIR}/chain_of_responsibility_pattern) 25 | add_subdirectory(${PROJECT_SOURCE_DIR}/interpreter_pattern) 26 | add_subdirectory(${PROJECT_SOURCE_DIR}/iterator_pattern) 27 | add_subdirectory(${PROJECT_SOURCE_DIR}/mediator_pattern) 28 | add_subdirectory(${PROJECT_SOURCE_DIR}/memento_pattern) 29 | add_subdirectory(${PROJECT_SOURCE_DIR}/observer_pattern) 30 | add_subdirectory(${PROJECT_SOURCE_DIR}/state_pattern) 31 | add_subdirectory(${PROJECT_SOURCE_DIR}/strategy_pattern) 32 | add_subdirectory(${PROJECT_SOURCE_DIR}/template_method_pattern) 33 | add_subdirectory(${PROJECT_SOURCE_DIR}/visitor_pattern) 34 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## 一、设计模式 2 | 3 | ​ 设计模式,是一套被反复使用、多数人知晓的、经过分类编目的、代码设计经验的总结。使用设计模式是为了可重用代码、让代码更容易被他人理解、保证代码可靠性、程序的重用性。 4 | 5 | ​ 设计模式其实就是开发过程中常见问题的解决方案,是解决问题的思路。 6 | 7 | ## 二、面向对象23种设计模式 8 | 9 | ### 创建型模式 10 | 11 | > **关注对象的创建** 12 | 13 | | 模式名称 | 中文名称 | 基本定义 | 14 | | :--------------- | :----------- | :----------------------------------------------------------- | 15 | | Singleton | 单例模式 | 保证一个类仅有一个实例,并且提供一个全局访问点。 | 16 | | Factory Method | 工厂方法模式 | 定义一个用于创建对象的接口,让子类决定将哪一个类实例化。工厂方法模式使一个类的实例化延迟到子类。 | 17 | | Abstract Factory | 抽象工厂 | 提供一个创建一系列相关或相互依赖对象的接口,而无需指定具体的类。 | 18 | | Builder | 建造者模式 | 讲一个复杂对象的构建和他的表示分离,使得同样的构建过程可以创建不同的表示 | 19 | | Prototype | 原型模式 | 用原型实例指定创建对象的种类,并且通过拷贝这个原型来创建新的对象。 | 20 | | Simple factory | 简单工厂模式 | 专门定义一个类来负责创建其他类的实例,被创建的实例通常都具有共同的父类 | 21 | 22 | 23 | ### 结构型模式 24 | 25 | > **关注类与对象之间的组合** 26 | 27 | | 模式名称 | 中文名称 | 基本定义 | 28 | | :-------- | :--------- | :----------------------------------------------------------- | 29 | | Adapter | 适配器模式 | 将一个类的接口转换成客户希望的另一个接口。适配器使得原来不兼容的接口可以一起工作。 | 30 | | Bridge | 桥接模式 | 将抽象部分与它的实现部分分离,使他们都可以独立变化 | 31 | | Composite | 组合模式 | 将对象组合成树形结构以表示“部分-整体”的层次结构。组合模式使得客户对单个对象对单个对象和复合对象的使用具有一致性。 | 32 | | Decorator | 装饰器模式 | 动态的给一个对象添加一些额外的职责。就扩展方式而言,装饰器模式比生成子类的方式更灵活 | 33 | | Facade | 外观模式 | 为子系统的一组接口提供一个一致的界面,Facade模式定义了一个高层的接口,这个接口使得这一个子系统更容易使用。 | 34 | | Flyweight | 享元模式 | 运用共享技术有效的支持大量细粒度对象。 | 35 | | Proxy | 代理模式 | 为其他对象提供一个代理以控制对这个对象的访问。 | 36 | 37 | ### 行为型模式 38 | 39 | > **关注对象和行为的分离** 40 | 41 | | 模式名称 | 中文名称 | 基本定义 | 42 | | :---------------------- | :----------- | :----------------------------------------------------------- | 43 | | Interpreter | 解释器模式 | 给定一个语言,定义它的文法的一种表示,并定义一个解释器,该解释器使用该表示来解释语言中的例子。 | 44 | | Template Method | 模板方法模式 | 定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤 | 45 | | Chain of Responsibility | 职责链模式 | 为解除请求的发送者和接收者之间的耦合,而使多个对象都有机会处理这个请求。讲这些对象连着一个链,并沿着这条链传递该请求,直到一个对象处理它。 | 46 | | Command | 命令模式 | 将一个请求封装成一个对象,从而使你可用不同的请求对客户进行参数化,对请求排队或记录请求日志,以及支持可取消操作。 | 47 | | Iterator | 迭代器模式 | 提供一种方法顺序访问一个聚合对象中的各个元素,而又不需要暴露该对象的内部表示。 | 48 | | Mediator | 媒介模式 | 用一个中介对象来封装一系列的对象交互。中介者使各对象不需要显示的相互引用,从而使其耦合松散,而且可以独立地改变他们之间的交互。 | 49 | | Memento | 备忘录模式 | 在不破坏封装性的前提下,捕获一个对象的内部状态,并在这个对象之外保存这个状态。这样就可以将这个对象恢复到保存的状态。 | 50 | | Observer | 观察者模式 | 定义对象间的一种一对多的依赖关系,以便当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并自动刷新。 | 51 | | State | 状态模式 | 允许一个对象在其内部状态改变时改变他的行为。对象看起来似乎修改了他所属的类。 | 52 | | Strategy | 策略模式 | 定义一系列算法,把它们一个个封装起来,并且使他们可相互替换,本模式使得算法的变化可独立于他的客户 | 53 | | Visitor | 访问者模式 | 表示一个作用于某对象结构的各元素的操作。他使你可以在不改变元素的类的前提下定义作用于这些元素的操作 | 54 | 55 | 56 | 57 | ![20180507194245467](https://i.loli.net/2021/01/26/sNjvd3CGhMU5oDQ.png) 58 | 59 | 60 | 61 | ## 三、设计模式六大原则详细解析 62 | 63 | - **单一职责**:一个类只负责一 项职责 64 | - **里氏替换原则**:子类可以扩展父类的功能,但不能改变原有父类的功能。尽量用子类替换父类 65 | - **依赖倒置原则**:抽象不应该依赖于细节,细节应当依赖于抽象,面向接口编程 66 | - **接口隔离原则**:使用多个专门的接口,而不使用单一的总接口。即 客户端不应该依赖于那些它不需要的接口 67 | - **迪米特原则**:最少知道原则,尽量降低类与类之间的耦合;一个对象应该对其他对象有最少的了解 68 | - **开闭原则**:对扩展开放,对修改关闭,能扩展不修改 69 | -------------------------------------------------------------------------------- /chain_of_responsibility_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(chain_of_responsibility_pattern) 4 | 5 | set(OUTPUTNAME chain_of_responsibility_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /chain_of_responsibility_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | struct request 5 | { 6 | int num; 7 | }; 8 | 9 | // 管理者. 10 | class manager 11 | { 12 | public: 13 | manager(const std::string& name) : _name(name) {} 14 | virtual ~manager() = default; 15 | 16 | void set_successor(manager* m) 17 | { 18 | _manager = m; 19 | } 20 | 21 | virtual void get_request(const request& req) = 0; 22 | 23 | protected: 24 | manager* _manager; 25 | std::string _name; 26 | }; 27 | 28 | // 经理. 29 | class common_manager : public manager 30 | { 31 | public: 32 | common_manager(const std::string& name) : manager(name) {} 33 | void get_request(const request& req) override 34 | { 35 | if (req.num >= 0 && req.num < 1000) 36 | { 37 | std::cout << _name << " 处理了请求:" << req.num << std::endl; 38 | } 39 | else 40 | { 41 | _manager->get_request(req); 42 | } 43 | } 44 | }; 45 | 46 | // 总监. 47 | class majordomo : public manager 48 | { 49 | public: 50 | majordomo(const std::string& name) : manager(name) {} 51 | void get_request(const request& req) override 52 | { 53 | if (req.num <= 5000) 54 | { 55 | std::cout << _name << " 处理了请求:" << req.num << std::endl; 56 | } 57 | else 58 | { 59 | _manager->get_request(req); 60 | } 61 | } 62 | }; 63 | 64 | class general_manager : public manager 65 | { 66 | public: 67 | general_manager(const std::string& name) : manager(name) {} 68 | void get_request(const request& req) override 69 | { 70 | std::cout << _name << " 处理了请求:" << req.num << std::endl; 71 | } 72 | }; 73 | 74 | int main() 75 | { 76 | manager* common = new common_manager("张经理"); 77 | manager* major = new majordomo("李总监"); 78 | general_manager* general = new general_manager("赵总"); 79 | common->set_successor(major); 80 | major->set_successor(general); 81 | 82 | request req {999}; 83 | common->get_request(req); 84 | 85 | req.num = 4999; 86 | common->get_request(req); 87 | 88 | req.num = 6999; 89 | common->get_request(req); 90 | 91 | delete general; 92 | delete major; 93 | delete common; 94 | 95 | return 0; 96 | } 97 | -------------------------------------------------------------------------------- /command_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(command_pattern) 4 | 5 | set(OUTPUTNAME command_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /command_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | // 烤肉师傅. 5 | class roast_cook 6 | { 7 | public: 8 | void make_mutton() 9 | { 10 | std::cout << "make mutton" << std::endl; 11 | } 12 | 13 | void make_chickenwing() 14 | { 15 | std::cout << "make chickenwing" << std::endl; 16 | } 17 | }; 18 | 19 | // 抽象命令类. 20 | class command 21 | { 22 | public: 23 | command(roast_cook* cook) : _roast_cook(cook) {} 24 | virtual ~command() {} 25 | virtual void execute() = 0; 26 | 27 | protected: 28 | roast_cook* _roast_cook; 29 | }; 30 | 31 | // 烤羊肉命令. 32 | class make_mutton_command : public command 33 | { 34 | public: 35 | make_mutton_command(roast_cook* cook) : command(cook) {} 36 | virtual void execute() 37 | { 38 | _roast_cook->make_mutton(); 39 | } 40 | }; 41 | 42 | // 烤鸡翅命令. 43 | class make_chickenwing_command : public command 44 | { 45 | public: 46 | make_chickenwing_command(roast_cook* cook) : command(cook) {} 47 | virtual void execute() 48 | { 49 | _roast_cook->make_chickenwing(); 50 | } 51 | }; 52 | 53 | // 服务员类. 54 | class waiter 55 | { 56 | public: 57 | void set_command(command* cmd) 58 | { 59 | std::cout << "set command" << std::endl; 60 | _command_vec.emplace_back(cmd); 61 | } 62 | 63 | void notify() 64 | { 65 | for (auto& cmd : _command_vec) 66 | { 67 | cmd->execute(); 68 | } 69 | } 70 | 71 | private: 72 | std::vector _command_vec; 73 | }; 74 | 75 | int main() 76 | { 77 | roast_cook* cook = new roast_cook(); 78 | command* cmd1 = new make_mutton_command(cook); 79 | command* cmd2 = new make_chickenwing_command(cook); 80 | waiter* girl = new waiter(); 81 | 82 | // 点菜. 83 | girl->set_command(cmd1); 84 | girl->set_command(cmd2); 85 | 86 | // 服务员通知厨师做菜. 87 | girl->notify(); 88 | 89 | delete girl; 90 | delete cmd1; 91 | delete cmd2; 92 | delete cook; 93 | 94 | return 0; 95 | } 96 | -------------------------------------------------------------------------------- /composite_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(composite_pattern) 4 | 5 | set(OUTPUTNAME composite_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /composite_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | class menu 6 | { 7 | public: 8 | virtual ~menu() = default; 9 | virtual void add(menu*) {} 10 | virtual menu* get_child(int) { return nullptr; } 11 | virtual void display()= 0; 12 | 13 | protected: 14 | menu() = default; 15 | menu(const std::string& name) : _name(name) {} 16 | 17 | std::string _name; 18 | }; 19 | 20 | class sub_menu : public menu 21 | { 22 | public: 23 | sub_menu() = default; 24 | sub_menu(const std::string& name) : menu(name) {} 25 | 26 | void display() override 27 | { 28 | std::cout << _name << std::endl; 29 | } 30 | }; 31 | 32 | class composit_menu : public menu 33 | { 34 | public: 35 | composit_menu() = default; 36 | composit_menu(const std::string& name) : menu(name) {} 37 | ~composit_menu() 38 | { 39 | for (auto& m : _menu_vec) 40 | { 41 | delete m; 42 | } 43 | } 44 | 45 | void add(menu* m) override 46 | { 47 | _menu_vec.emplace_back(m); 48 | } 49 | 50 | menu* get_child(int index) override 51 | { 52 | return _menu_vec[index]; 53 | } 54 | 55 | void display() override 56 | { 57 | std::cout << "+" << _name << std::endl; 58 | for (auto& m : _menu_vec) 59 | { 60 | std::cout << "|-"; 61 | m->display(); 62 | } 63 | } 64 | 65 | private: 66 | std::vector _menu_vec; 67 | }; 68 | 69 | int main() 70 | { 71 | menu* m1 = new composit_menu("国内新闻"); 72 | m1->add(new sub_menu("时事新闻")); 73 | m1->add(new sub_menu("社会新闻")); 74 | m1->display(); 75 | 76 | menu* m2 = new composit_menu("国际新闻"); 77 | m2->add(new sub_menu("国际要闻")); 78 | m2->add(new sub_menu("环球视野")); 79 | m2->display(); 80 | 81 | delete m1; 82 | delete m2; 83 | return 0; 84 | } 85 | 86 | -------------------------------------------------------------------------------- /decorator_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(decorator_pattern) 4 | 5 | set(OUTPUTNAME decorator_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /decorator_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class tank 5 | { 6 | public: 7 | virtual ~tank() = default; 8 | virtual void shot() = 0; 9 | virtual void run() = 0; 10 | }; 11 | 12 | class t50 : public tank 13 | { 14 | public: 15 | void shot() override 16 | { 17 | std::cout << "tank t50 shot" << std::endl; 18 | } 19 | 20 | void run() override 21 | { 22 | std::cout << "tank t50 run" << std::endl; 23 | } 24 | }; 25 | 26 | class t75 : public tank 27 | { 28 | public: 29 | void shot() override 30 | { 31 | std::cout << "tank t75 shot" << std::endl; 32 | } 33 | 34 | void run() override 35 | { 36 | std::cout << "tank t75 run" << std::endl; 37 | } 38 | }; 39 | 40 | class decorator : public tank 41 | { 42 | public: 43 | decorator(tank* t) : _tank(t) {} 44 | 45 | void shot() override 46 | { 47 | _tank->shot(); 48 | } 49 | 50 | void run() override 51 | { 52 | _tank->run(); 53 | } 54 | 55 | protected: 56 | tank* _tank; 57 | }; 58 | 59 | class infrared_decorator : public decorator 60 | { 61 | public: 62 | infrared_decorator(tank* t) : decorator(t) {} 63 | 64 | void run() override 65 | { 66 | _tank->run(); 67 | set_infrared("+Infrared"); 68 | std::cout << get_infrared() << std::endl; 69 | } 70 | 71 | void shot() override 72 | { 73 | _tank->shot(); 74 | } 75 | 76 | void set_infrared(const std::string& infrared) 77 | { 78 | _infrared = infrared; 79 | } 80 | 81 | std::string get_infrared() const 82 | { 83 | return _infrared; 84 | } 85 | 86 | private: 87 | std::string _infrared; 88 | }; 89 | 90 | class amphibian_decorator : public decorator 91 | { 92 | public: 93 | amphibian_decorator(tank* t) : decorator(t) {} 94 | 95 | void run() override 96 | { 97 | _tank->run(); 98 | set_amphibian("+Amphibian"); 99 | std::cout << get_amphibian() << std::endl; 100 | } 101 | 102 | void shot() override 103 | { 104 | _tank->shot(); 105 | } 106 | 107 | void set_amphibian(const std::string& amphibian) 108 | { 109 | _amphibian = amphibian; 110 | } 111 | 112 | std::string get_amphibian() const 113 | { 114 | return _amphibian; 115 | } 116 | 117 | private: 118 | std::string _amphibian; 119 | }; 120 | 121 | int main() 122 | { 123 | tank* t1 = new t50(); 124 | tank* t2 = new infrared_decorator(t1); 125 | t2->shot(); 126 | t2->run(); 127 | 128 | delete t1; 129 | delete t2; 130 | 131 | return 0; 132 | } 133 | 134 | -------------------------------------------------------------------------------- /facade_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(facade_pattern) 4 | 5 | set(OUTPUTNAME facade_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /facade_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | class scanner 4 | { 5 | public: 6 | void scan() 7 | { 8 | std::cout << "词法分析" << std::endl; 9 | } 10 | }; 11 | 12 | class parser 13 | { 14 | public: 15 | void parse() 16 | { 17 | std::cout << "语法分析" << std::endl; 18 | } 19 | }; 20 | 21 | class gen_mid_code 22 | { 23 | public: 24 | void gen_code() 25 | { 26 | std::cout << "产生中间代码" << std::endl; 27 | } 28 | }; 29 | 30 | class gen_machine_code 31 | { 32 | public: 33 | void gen_code() 34 | { 35 | std::cout << "产生机器码" << std::endl; 36 | } 37 | }; 38 | 39 | class compiler 40 | { 41 | public: 42 | void run() 43 | { 44 | scanner s; 45 | s.scan(); 46 | 47 | parser p; 48 | p.parse(); 49 | 50 | gen_mid_code min_code; 51 | min_code.gen_code(); 52 | 53 | gen_machine_code machine_code; 54 | machine_code.gen_code(); 55 | } 56 | }; 57 | 58 | int main() 59 | { 60 | compiler c; 61 | c.run(); 62 | return 0; 63 | } 64 | -------------------------------------------------------------------------------- /factory_method_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(factory_method_pattern) 4 | 5 | set(OUTPUTNAME factory_method_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /factory_method_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | class product 4 | { 5 | public: 6 | virtual ~product() {} 7 | }; 8 | 9 | class phone : public product 10 | { 11 | public: 12 | phone() 13 | { 14 | std::cout << "make phone" << std::endl; 15 | } 16 | }; 17 | 18 | class tv : public product 19 | { 20 | public: 21 | tv() 22 | { 23 | std::cout << "make tv" << std::endl; 24 | } 25 | }; 26 | 27 | class factory 28 | { 29 | public: 30 | virtual ~factory() {} 31 | virtual product* make_product() = 0; 32 | }; 33 | 34 | class phone_factory : public factory 35 | { 36 | public: 37 | virtual product* make_product() 38 | { 39 | return new phone(); 40 | } 41 | }; 42 | 43 | class tv_factory : public factory 44 | { 45 | public: 46 | virtual product* make_product() 47 | { 48 | return new tv(); 49 | } 50 | }; 51 | 52 | int main() 53 | { 54 | factory* factory1 = new phone_factory(); 55 | product* product1 = factory1->make_product(); 56 | 57 | factory* factory2 = new tv_factory(); 58 | product* product2 = factory2->make_product(); 59 | 60 | delete factory1; 61 | delete product1; 62 | delete factory2; 63 | delete product2; 64 | 65 | return 0; 66 | } 67 | -------------------------------------------------------------------------------- /flyweight_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(flyweight_pattern) 4 | 5 | set(OUTPUTNAME flyweight_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /flyweight_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | class character 6 | { 7 | public: 8 | virtual ~character() = default; 9 | virtual void set_size(int, int) = 0; 10 | virtual void display() = 0; 11 | 12 | protected: 13 | std::string _symbol; 14 | int _weight = 0; 15 | int _height = 0; 16 | }; 17 | 18 | class character_a : public character 19 | { 20 | public: 21 | character_a() 22 | { 23 | _symbol = "A"; 24 | _weight = 100; 25 | _height = 200; 26 | } 27 | 28 | void set_size(int w, int h) override 29 | { 30 | _weight = w; 31 | _height = h; 32 | } 33 | 34 | void display() override 35 | { 36 | std::cout << "character_a: " << _symbol << "(" << _weight << "," << _height << ")" << std::endl; 37 | } 38 | }; 39 | 40 | class character_b : public character 41 | { 42 | public: 43 | character_b() 44 | { 45 | _symbol = "B"; 46 | _weight = 100; 47 | _height = 200; 48 | } 49 | 50 | void set_size(int w, int h) override 51 | { 52 | _weight = w; 53 | _height = h; 54 | } 55 | 56 | void display() override 57 | { 58 | std::cout << "character_b: " << _symbol << "(" << _weight << "," << _height << ")" << std::endl; 59 | } 60 | }; 61 | 62 | class character_factory 63 | { 64 | public: 65 | character_factory() 66 | { 67 | _character_map.emplace("A", new character_a()); 68 | _character_map.emplace("B", new character_b()); 69 | } 70 | 71 | ~character_factory() 72 | { 73 | for (auto& iter : _character_map) 74 | { 75 | delete iter.second; 76 | } 77 | } 78 | 79 | character* get_character(const std::string& key) 80 | { 81 | auto iter = _character_map.find(key); 82 | if (iter != _character_map.end()) 83 | { 84 | return iter->second; 85 | } 86 | return nullptr; 87 | } 88 | 89 | private: 90 | std::map _character_map; 91 | }; 92 | 93 | int main() 94 | { 95 | character_factory* f1 = new character_factory(); 96 | character* c1 = f1->get_character("A"); 97 | c1->display(); 98 | 99 | character* c2 = f1->get_character("B"); 100 | c2->set_size(500, 800); 101 | c2->display(); 102 | 103 | delete f1; 104 | 105 | return 0; 106 | } 107 | -------------------------------------------------------------------------------- /interpreter_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(interpreter_pattern) 4 | 5 | set(OUTPUTNAME interpreter_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /interpreter_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | class context 6 | { 7 | public: 8 | void add_value(const std::string& key, int value) 9 | { 10 | _value_map.emplace(key, value); 11 | } 12 | 13 | int get_value(const std::string& key) 14 | { 15 | return _value_map[key]; 16 | } 17 | 18 | private: 19 | std::map _value_map; 20 | }; 21 | 22 | class expression 23 | { 24 | public: 25 | virtual ~expression() = default; 26 | virtual int interpreter(const context&) = 0; 27 | }; 28 | 29 | class add_nonterminal_expression : public expression 30 | { 31 | public: 32 | add_nonterminal_expression(expression* left, expression* right) 33 | : _left(left), _right(right) {} 34 | 35 | int interpreter(const context& c) override 36 | { 37 | return _left->interpreter(c) + _right->interpreter(c); 38 | } 39 | 40 | private: 41 | expression* _left; 42 | expression* _right; 43 | }; 44 | 45 | class subtract_nonterminal_expression : public expression 46 | { 47 | public: 48 | subtract_nonterminal_expression(expression* left, expression* right) 49 | : _left(left), _right(right) {} 50 | 51 | int interpreter(const context& c) override 52 | { 53 | return _left->interpreter(c) - _right->interpreter(c); 54 | } 55 | 56 | private: 57 | expression* _left; 58 | expression* _right; 59 | }; 60 | 61 | class terminal_expression : public expression 62 | { 63 | public: 64 | terminal_expression(int i) : _i(i) {} 65 | 66 | int interpreter(const context&) override 67 | { 68 | return _i; 69 | } 70 | 71 | private: 72 | int _i; 73 | }; 74 | 75 | int main() 76 | { 77 | context c; 78 | c.add_value("a", 7); 79 | c.add_value("b", 8); 80 | c.add_value("c", 2); 81 | 82 | terminal_expression* t1 = new terminal_expression(c.get_value("a")); 83 | terminal_expression* t2 = new terminal_expression(c.get_value("b")); 84 | subtract_nonterminal_expression *sub = new subtract_nonterminal_expression(t1, t2); 85 | 86 | terminal_expression* t3 = new terminal_expression(c.get_value("c")); 87 | add_nonterminal_expression* add = new add_nonterminal_expression(sub, t3); 88 | 89 | std::cout << "a - b + c = " << add->interpreter(c) << std::endl; 90 | 91 | delete t1; 92 | delete t2; 93 | delete t3; 94 | 95 | return 0; 96 | } 97 | 98 | -------------------------------------------------------------------------------- /iterator_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(iterator_pattern) 4 | 5 | set(OUTPUTNAME iterator_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /iterator_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | template 5 | class iterator_base 6 | { 7 | public: 8 | virtual ~iterator_base() = default; 9 | virtual void first() = 0; 10 | virtual void next() = 0; 11 | virtual Item* current_item() = 0; 12 | virtual bool is_done() = 0; 13 | }; 14 | 15 | template 16 | class concrete_aggregate; 17 | 18 | template 19 | class concrete_iterator : public iterator_base 20 | { 21 | public: 22 | concrete_iterator(concrete_aggregate* a) : _aggr(a) {} 23 | 24 | void first() override 25 | { 26 | _current = 0; 27 | } 28 | 29 | void next() override 30 | { 31 | if (_current < _aggr->len()) 32 | { 33 | ++_current; 34 | } 35 | } 36 | 37 | Item* current_item() override 38 | { 39 | if (_current < _aggr->len()) 40 | { 41 | return &(*_aggr)[_current]; 42 | } 43 | return nullptr; 44 | } 45 | 46 | bool is_done() override 47 | { 48 | return _current == _aggr->len(); 49 | } 50 | 51 | private: 52 | concrete_aggregate* _aggr; 53 | int _current = 0; 54 | }; 55 | 56 | template 57 | class aggergate 58 | { 59 | public: 60 | virtual ~aggergate() = default; 61 | virtual iterator_base* create_iterator() = 0; 62 | }; 63 | 64 | template 65 | class concrete_aggregate : public aggergate 66 | { 67 | public: 68 | iterator_base* create_iterator() override 69 | { 70 | return new concrete_iterator(this); 71 | } 72 | 73 | Item& operator[](int index) 74 | { 75 | return _item_vec[index]; 76 | } 77 | 78 | int len() const 79 | { 80 | return _item_vec.size(); 81 | } 82 | 83 | private: 84 | std::vector _item_vec {1, 2, 3}; 85 | }; 86 | 87 | int main() 88 | { 89 | aggergate* aggr = new concrete_aggregate(); 90 | iterator_base* iter = aggr->create_iterator(); 91 | for (iter->first(); !iter->is_done(); iter->next()) 92 | { 93 | std::cout << *(iter->current_item()) << std::endl; 94 | } 95 | 96 | delete iter; 97 | delete aggr; 98 | 99 | return 0; 100 | } 101 | -------------------------------------------------------------------------------- /mediator_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(mediator_pattern) 4 | 5 | set(OUTPUTNAME mediator_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /mediator_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | class colleage 6 | { 7 | public: 8 | colleage(const std::string& name) : _name(name) {}; 9 | virtual ~colleage() = default; 10 | 11 | void set_name(const std::string& name) { _name = name; } 12 | std::string get_name() const { return _name; } 13 | 14 | void set_content(const std::string& content) { _content = content; } 15 | std::string get_content() const { return _content; } 16 | 17 | virtual void talk() = 0; 18 | 19 | private: 20 | std::string _name; 21 | std::string _content; 22 | }; 23 | 24 | class monitor : public colleage 25 | { 26 | public: 27 | monitor(const std::string& name) : colleage(name) {} 28 | void talk() override 29 | { 30 | std::cout << "班长 " << get_name() << " 说:" << get_content() << std::endl; 31 | } 32 | }; 33 | 34 | class secretary : public colleage 35 | { 36 | public: 37 | secretary(const std::string& name) : colleage(name) {} 38 | void talk() override 39 | { 40 | std::cout << "团支书 " << get_name() << " 说:" << get_content() << std::endl; 41 | } 42 | }; 43 | 44 | class student_a : public colleage 45 | { 46 | public: 47 | student_a(const std::string& name) : colleage(name) {} 48 | void talk() override 49 | { 50 | std::cout << "学生A " << get_name() << " 说:" << get_content() << std::endl; 51 | } 52 | }; 53 | 54 | class student_b : public colleage 55 | { 56 | public: 57 | student_b(const std::string& name) : colleage(name) {} 58 | void talk() override 59 | { 60 | std::cout << "学生B " << get_name() << " 说:" << get_content() << std::endl; 61 | } 62 | }; 63 | 64 | class mediator 65 | { 66 | public: 67 | std::vector _colleage_vec; 68 | virtual ~mediator() = default; 69 | virtual void add_student(colleage* c) 70 | { 71 | _colleage_vec.emplace_back(c); 72 | } 73 | virtual void notiry(colleage*) = 0; 74 | }; 75 | 76 | class qq_mediator : public mediator 77 | { 78 | public: 79 | virtual void notiry(colleage* c) override 80 | { 81 | c->talk(); 82 | for (std::size_t i = 0; i < _colleage_vec.size(); ++i) 83 | { 84 | if (c != _colleage_vec[i]) 85 | { 86 | _colleage_vec[i]->talk(); 87 | } 88 | } 89 | } 90 | }; 91 | 92 | int main() 93 | { 94 | qq_mediator qq; 95 | monitor* m = new monitor("Jack"); 96 | secretary* s = new secretary("Tom"); 97 | student_a* a = new student_a("Frank"); 98 | student_b* b = new student_b("Tim"); 99 | 100 | qq.add_student(m); 101 | qq.add_student(s); 102 | qq.add_student(a); 103 | qq.add_student(b); 104 | 105 | m->set_content("明天开始放假!"); 106 | qq.notiry(m); 107 | 108 | delete m; 109 | delete s; 110 | delete a; 111 | delete b; 112 | 113 | return 0; 114 | } 115 | -------------------------------------------------------------------------------- /memento_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(memento_pattern) 4 | 5 | set(OUTPUTNAME memento_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /memento_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | struct memento 5 | { 6 | int vitality; 7 | int attack; 8 | int defense; 9 | }; 10 | 11 | class game_role 12 | { 13 | public: 14 | memento save() 15 | { 16 | return _memento; 17 | } 18 | 19 | void load(memento m) 20 | { 21 | _memento = m; 22 | } 23 | 24 | void show() 25 | { 26 | std::cout << "vitality: " << _memento.vitality << std::endl; 27 | std::cout << "attack: " << _memento.attack << std::endl; 28 | std::cout << "defense: " << _memento.defense << std::endl; 29 | } 30 | 31 | void attack() 32 | { 33 | _memento.vitality -= 10; 34 | _memento.attack -= 10; 35 | _memento.defense -= 10; 36 | } 37 | 38 | private: 39 | memento _memento {100, 100, 100}; 40 | }; 41 | 42 | class caretake 43 | { 44 | public: 45 | void save(memento m) 46 | { 47 | _memento_vec.emplace_back(m); 48 | } 49 | 50 | memento load(int state) 51 | { 52 | return _memento_vec[state]; 53 | } 54 | 55 | private: 56 | std::vector _memento_vec; 57 | }; 58 | 59 | int main() 60 | { 61 | caretake c; 62 | game_role role; 63 | role.show(); 64 | c.save(role.save()); 65 | role.attack(); 66 | role.show(); 67 | role.load(c.load(0)); 68 | role.show(); 69 | 70 | return 0; 71 | } 72 | 73 | -------------------------------------------------------------------------------- /observer_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(observer_pattern) 4 | 5 | set(OUTPUTNAME observer_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /observer_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | class observer 6 | { 7 | public: 8 | virtual ~observer() = default; 9 | virtual void update() = 0; 10 | }; 11 | 12 | class blog 13 | { 14 | public: 15 | virtual ~blog() = default; 16 | 17 | void attach(observer* o) 18 | { 19 | _observer_list.emplace_back(o); 20 | } 21 | 22 | void remove(observer* o) 23 | { 24 | _observer_list.remove(o); 25 | } 26 | 27 | void notify() 28 | { 29 | for (auto& iter : _observer_list) 30 | { 31 | iter->update(); 32 | } 33 | } 34 | 35 | virtual void set_status(const std::string& status) = 0; 36 | virtual std::string get_status() const = 0; 37 | 38 | protected: 39 | std::string _status; 40 | 41 | private: 42 | std::list _observer_list; 43 | }; 44 | 45 | class blog_csdn : public blog 46 | { 47 | public: 48 | blog_csdn(const std::string& title) : _title(title) {} 49 | 50 | void set_status(const std::string& status) override 51 | { 52 | _status = "CSDN通知:" + _title + status; 53 | } 54 | 55 | std::string get_status() const override 56 | { 57 | return _status; 58 | } 59 | 60 | private: 61 | std::string _title; 62 | }; 63 | 64 | class observer_blog : public observer 65 | { 66 | public: 67 | observer_blog(const std::string& name, blog* b) : _name(name), _blog(b) {} 68 | 69 | void update() override 70 | { 71 | std::cout << _name << "------------" << _blog->get_status() << std::endl; 72 | } 73 | 74 | private: 75 | std::string _name; 76 | blog* _blog; 77 | }; 78 | 79 | int main() 80 | { 81 | blog* b = new blog_csdn("chxuan"); 82 | observer* o = new observer_blog("cx", b); 83 | b->attach(o); 84 | b->set_status("C++"); 85 | b->notify(); 86 | delete b; 87 | delete o; 88 | return 0; 89 | } 90 | 91 | -------------------------------------------------------------------------------- /prototype_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(prototype_pattern) 4 | 5 | set(OUTPUTNAME prototype_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /prototype_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | class resume 7 | { 8 | public: 9 | resume() {} 10 | virtual ~resume() {} 11 | virtual resume* clone() { return nullptr; } 12 | virtual void set(char*) {} 13 | virtual void show() {} 14 | 15 | protected: 16 | char* _name = nullptr; 17 | }; 18 | 19 | class resume_a : public resume 20 | { 21 | public: 22 | resume_a(const char* str) 23 | { 24 | if (str == nullptr) 25 | { 26 | _name = new char[1]; 27 | _name[0] = '\0'; 28 | } 29 | else 30 | { 31 | _name = new char[strlen(str) + 1]; 32 | strcpy(_name, str); 33 | } 34 | } 35 | 36 | ~resume_a() 37 | { 38 | if (_name != nullptr) 39 | { 40 | delete [] _name; 41 | _name = nullptr; 42 | } 43 | } 44 | 45 | resume_a(const resume_a& other) 46 | { 47 | if (_name != nullptr) 48 | { 49 | delete [] _name; 50 | _name = nullptr; 51 | } 52 | _name = new char[strlen(other._name) + 1]; 53 | strcpy(_name, other._name); 54 | } 55 | 56 | virtual resume_a* clone() 57 | { 58 | return new resume_a(*this); 59 | } 60 | 61 | virtual void show() 62 | { 63 | std::cout << "resume_a name: " << _name << std::endl; 64 | } 65 | }; 66 | 67 | int main() 68 | { 69 | resume* r1 = new resume_a("A"); 70 | resume* r2 = r1->clone(); 71 | r1->show(); 72 | delete r1; 73 | r2->show(); 74 | delete r2; 75 | return 0; 76 | } 77 | 78 | -------------------------------------------------------------------------------- /proxy_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(proxy_pattern) 4 | 5 | set(OUTPUTNAME proxy_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /proxy_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class image 5 | { 6 | public: 7 | image() = default; 8 | image(const std::string& name) : _image_name(name) {} 9 | virtual ~image() = default; 10 | virtual void show() = 0; 11 | 12 | protected: 13 | std::string _image_name; 14 | }; 15 | 16 | class big_image : public image 17 | { 18 | public: 19 | big_image(const std::string& name) : image(name) {} 20 | void show() override 21 | { 22 | std::cout << "show big image: " << _image_name << std::endl; 23 | } 24 | }; 25 | 26 | class big_image_proxy : public image 27 | { 28 | public: 29 | big_image_proxy(const std::string& name) : image(name) {} 30 | ~big_image_proxy() 31 | { 32 | delete _big_image; 33 | } 34 | 35 | void show() override 36 | { 37 | _big_image = new big_image(_image_name); 38 | _big_image->show(); 39 | } 40 | 41 | private: 42 | big_image* _big_image; 43 | }; 44 | 45 | int main() 46 | { 47 | image* img = new big_image_proxy("proxy.jpg"); 48 | img->show(); 49 | delete img; 50 | return 0; 51 | } 52 | -------------------------------------------------------------------------------- /simple_factory_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(simple_factory_pattern) 4 | 5 | set(OUTPUTNAME simple_factory_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /simple_factory_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class product 5 | { 6 | public: 7 | virtual ~product() {} 8 | }; 9 | 10 | class phone : public product 11 | { 12 | public: 13 | phone() 14 | { 15 | std::cout << "make phone" << std::endl; 16 | } 17 | }; 18 | 19 | class tv : public product 20 | { 21 | public: 22 | tv() 23 | { 24 | std::cout << "make tv" << std::endl; 25 | } 26 | }; 27 | 28 | class simple_factory 29 | { 30 | public: 31 | static product* create(const std::string& product_name) 32 | { 33 | if (product_name == "phone") 34 | { 35 | return new phone(); 36 | } 37 | else if (product_name == "tv") 38 | { 39 | return new tv(); 40 | } 41 | else 42 | { 43 | return nullptr; 44 | } 45 | } 46 | }; 47 | 48 | int main() 49 | { 50 | product* product1 = simple_factory::create("phone"); 51 | product* product2 = simple_factory::create("tv"); 52 | delete product1; 53 | delete product2; 54 | return 0; 55 | } 56 | 57 | -------------------------------------------------------------------------------- /singleton_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(singleton_pattern) 4 | 5 | set(OUTPUTNAME singleton_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /singleton_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | class single 4 | { 5 | public: 6 | single() = default; 7 | single(const single&) = delete; 8 | single& operator=(const single&) = delete; 9 | 10 | static single& get_instance() 11 | { 12 | static single s; 13 | return s; 14 | } 15 | 16 | void print() 17 | { 18 | std::cout << "Hello world" << std::endl; 19 | } 20 | }; 21 | 22 | int main() 23 | { 24 | single::get_instance().print(); 25 | single::get_instance().print(); 26 | return 0; 27 | } 28 | 29 | -------------------------------------------------------------------------------- /state_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(state_pattern) 4 | 5 | set(OUTPUTNAME state_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /state_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class war; 5 | 6 | class state 7 | { 8 | public: 9 | virtual ~state() = default; 10 | virtual void get_current_state(war*) = 0; 11 | }; 12 | 13 | class war 14 | { 15 | public: 16 | war(state* s) : _state(s) {} 17 | ~war() { delete _state; } 18 | int get_days() const { return _days; } 19 | void set_days(int days) { _days = days; } 20 | void get_state() { _state->get_current_state(this); } 21 | void set_state(state* s) { delete _state; _state = s; } 22 | 23 | private: 24 | state* _state; 25 | int _days = 0; 26 | }; 27 | 28 | class end_state : public state 29 | { 30 | public: 31 | void get_current_state(war*) override 32 | { 33 | std::cout << "战争结束" << std::endl; 34 | } 35 | }; 36 | 37 | class anaphase_state : public state 38 | { 39 | public: 40 | void get_current_state(war* w) override 41 | { 42 | if (w->get_days() < 30) 43 | { 44 | std::cout << w->get_days() << ", 后期" << std::endl; 45 | } 46 | else 47 | { 48 | w->set_state(new end_state()); 49 | w->get_state(); 50 | } 51 | } 52 | }; 53 | 54 | class metaphase_state : public state 55 | { 56 | public: 57 | void get_current_state(war* w) override 58 | { 59 | if (w->get_days() < 20) 60 | { 61 | std::cout << w->get_days() << ", 中期" << std::endl; 62 | } 63 | else 64 | { 65 | w->set_state(new anaphase_state()); 66 | w->get_state(); 67 | } 68 | } 69 | }; 70 | 71 | class prophase_state : public state 72 | { 73 | public: 74 | void get_current_state(war* w) 75 | { 76 | if (w->get_days() < 10) 77 | { 78 | std::cout << w->get_days() << ", 前期" << std::endl; 79 | } 80 | else 81 | { 82 | w->set_state(new metaphase_state()); 83 | w->get_state(); 84 | } 85 | } 86 | }; 87 | 88 | int main() 89 | { 90 | war* w = new war(new prophase_state()); 91 | for (int i = 1; i < 40; ++i) 92 | { 93 | w->set_days(i); 94 | w->get_state(); 95 | } 96 | 97 | delete w; 98 | return 0; 99 | } 100 | -------------------------------------------------------------------------------- /strategy_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(strategy_pattern) 4 | 5 | set(OUTPUTNAME strategy_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /strategy_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | class weapon_behavior 4 | { 5 | public: 6 | virtual ~weapon_behavior() = default; 7 | virtual void use_weapon() = 0; 8 | }; 9 | 10 | class ak47 : public weapon_behavior 11 | { 12 | public: 13 | void use_weapon() override 14 | { 15 | std::cout << "use ak47 to shoot!" << std::endl; 16 | } 17 | }; 18 | 19 | class knife : public weapon_behavior 20 | { 21 | public: 22 | void use_weapon() override 23 | { 24 | std::cout << "use knife to kill!" << std::endl; 25 | } 26 | }; 27 | 28 | class character 29 | { 30 | public: 31 | virtual ~character() = default; 32 | 33 | void set_weapon(weapon_behavior* weapon) 34 | { 35 | weapon_ = weapon; 36 | } 37 | 38 | virtual void fight() = 0; 39 | 40 | protected: 41 | weapon_behavior* weapon_ = nullptr; 42 | }; 43 | 44 | class king : public character 45 | { 46 | public: 47 | void fight() override 48 | { 49 | std::cout << "the king:"; 50 | if (weapon_ == nullptr) 51 | { 52 | std::cout << "You do not have a weapon! please set weapon!" << std::endl; 53 | } 54 | else 55 | { 56 | weapon_->use_weapon(); 57 | } 58 | } 59 | }; 60 | 61 | int main() 62 | { 63 | weapon_behavior* a = new ak47(); 64 | weapon_behavior* k = new knife(); 65 | 66 | character* c = new king(); 67 | c->fight(); 68 | 69 | c->set_weapon(a); 70 | c->fight(); 71 | 72 | c->set_weapon(k); 73 | c->fight(); 74 | 75 | delete a; 76 | delete k; 77 | delete c; 78 | 79 | return 0; 80 | } 81 | -------------------------------------------------------------------------------- /template_method_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(template_method_pattern) 4 | 5 | set(OUTPUTNAME template_method_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /template_method_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | template 4 | class caffeine_beverage 5 | { 6 | public: 7 | virtual ~caffeine_beverage() = default; 8 | 9 | void prepare_recipe() 10 | { 11 | boil_water(); 12 | brew(); 13 | pour_in_cup(); 14 | add_condiments(); 15 | } 16 | 17 | void boil_water() 18 | { 19 | std::cout << "把水煮沸" << std::endl; 20 | } 21 | 22 | void brew() 23 | { 24 | static_cast(this)->brew(); 25 | } 26 | 27 | void pour_in_cup() 28 | { 29 | std::cout << "把咖啡倒进杯子" << std::endl; 30 | } 31 | 32 | void add_condiments() 33 | { 34 | static_cast(this)->add_condiments(); 35 | } 36 | }; 37 | 38 | class coffee : public caffeine_beverage 39 | { 40 | public: 41 | void brew() 42 | { 43 | std::cout << "用沸水冲泡咖啡" << std::endl; 44 | } 45 | 46 | void add_condiments() 47 | { 48 | std::cout << "加糖和牛奶" << std::endl; 49 | } 50 | }; 51 | 52 | class tea : public caffeine_beverage 53 | { 54 | public: 55 | void brew() 56 | { 57 | std::cout << "用沸水冲泡茶叶" << std::endl; 58 | } 59 | 60 | void add_condiments() 61 | { 62 | std::cout << "加柠檬" << std::endl; 63 | } 64 | }; 65 | 66 | int main() 67 | { 68 | std::cout << "冲杯咖啡" << std::endl; 69 | coffee c; 70 | c.prepare_recipe(); 71 | std::cout << std::endl; 72 | std::cout << "冲杯茶" << std::endl; 73 | tea t; 74 | t.prepare_recipe(); 75 | 76 | return 0; 77 | } 78 | -------------------------------------------------------------------------------- /visitor_pattern/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8) 2 | 3 | project(visitor_pattern) 4 | 5 | set(OUTPUTNAME visitor_pattern) 6 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++14") 7 | 8 | aux_source_directory(. DIR_SRCS) 9 | add_executable(${OUTPUTNAME} ${DIR_SRCS}) 10 | 11 | -------------------------------------------------------------------------------- /visitor_pattern/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | class visitor; 4 | 5 | class element 6 | { 7 | public: 8 | virtual ~element() = default; 9 | virtual void accept(visitor* v) = 0; 10 | virtual void do_something() = 0; 11 | }; 12 | 13 | class visitor 14 | { 15 | public: 16 | virtual ~visitor() = default; 17 | virtual void visit(element* e) = 0; 18 | }; 19 | 20 | class element_a : public element 21 | { 22 | public: 23 | virtual void accept(visitor* v) override final 24 | { 25 | v->visit(this); 26 | } 27 | 28 | virtual void do_something() override final 29 | { 30 | std::cout << "do something" << std::endl; 31 | } 32 | }; 33 | 34 | class visitor_a : public visitor 35 | { 36 | public: 37 | virtual void visit(element* e) override final 38 | { 39 | e->do_something(); 40 | } 41 | }; 42 | 43 | int main() 44 | { 45 | element* e = new element_a(); 46 | visitor* v = new visitor_a(); 47 | e->accept(v); 48 | 49 | delete e; 50 | delete v; 51 | 52 | return 0; 53 | } 54 | --------------------------------------------------------------------------------