做博客网站最好用什么系统,推广联盟平台,深圳机票网站建设,望牛墩镇仿做网站1、创建型模式#xff08;常见的设计模式#xff09;
Factory 模式#xff08;工厂模式#xff0c;被实例化的子类#xff09;
在面向对象系统设计中经常可以遇到以下的两类问题#xff1a;
下面是第一类问题和代码示例#xff1a;我们经常会抽象出一些类的公共接口以…1、创建型模式常见的设计模式
Factory 模式工厂模式被实例化的子类
在面向对象系统设计中经常可以遇到以下的两类问题
下面是第一类问题和代码示例我们经常会抽象出一些类的公共接口以形成抽象基类或者接口。这样我们可以通过声明一个指向基类的指针来指向实际的子类实现达到了多态的目的。所以就不得不在要用到子类的地方写new 对象。这样实体类的使用者必须知道实际的子类名称以及会使程序的扩展性和维护变得越来越困难。
#include iostream// 抽象基类或接口
class Animal {
public:virtual void makeSound() 0; // 纯虚函数
};// 具体子类
class Dog : public Animal {
public:void makeSound() override {std::cout Woof! std::endl;}
};class Cat : public Animal {
public:void makeSound() override {std::cout Meow! std::endl;}
};int main() {Animal* animal;// 通过指向基类的指针指向具体的子类实例animal new Dog();animal-makeSound();animal new Cat();animal-makeSound();return 0;
}
在上述示例中我们定义了一个抽象基类 Animal其中包含一个纯虚函数 makeSound()。然后我们派生出两个具体的子类 Dog 和 Cat并分别实现了 makeSound() 方法。在 main() 函数中我们使用指向基类的指针 animal通过 new 实例化具体的子类并调用其方法。这样可以实现多态性但使用者需要知道具体的子类名称不利于程序的扩展性和维护。
还有一种情况就是在父类中并不知道具体要实例化哪一个具体的子类。只能在父类中写方法调用具体调用哪一个类的方法交给子类实现。
#include iostream// 抽象基类
class Animal {
public:virtual void makeSound() 0; // 纯虚函数void performAction() {std::cout Performing action: ;makeSound();}
};// 具体子类
class Dog : public Animal {
public:void makeSound() override {std::cout Woof! std::endl;}
};class Cat : public Animal {
public:void makeSound() override {std::cout Meow! std::endl;}
};int main() {Animal* animal nullptr;int choice;std::cout Enter 1 for Dog, 2 for Cat: ;std::cin choice;// 根据用户的选择实例化不同的子类if (choice 1) {animal new Dog();} else if (choice 2) {animal new Cat();} else {std::cout Invalid choice std::endl;return 0;}animal-performAction();delete animal;return 0;
}
在上述示例中我们仍然有一个抽象基类 Animal其中包含一个纯虚函数 makeSound()。不同之处在于在 Animal 类中我们添加了一个 performAction() 方法该方法调用了 makeSound() 方法。在 main() 函数中根据用户的选择实例化不同的子类并通过基类指针调用 performAction() 方法。这样具体调用哪个子类的方法由子类自己实现父类并不知道具体的子类实例化。
以上两个问题也就引出了 Factory 模式的两个最重要的功能 1定义创建对象的接口封装了对象的创建。 2使得具体化类的工作延迟到了子类中。 工厂模式代码示例
#include iostream
#include string// 抽象产品类
class Product {
public:virtual void use() const 0;
};// 具体产品类 A
class ConcreteProductA : public Product {
public:void use() const override {std::cout Using ConcreteProductA std::endl;}
};// 具体产品类 B
class ConcreteProductB : public Product {
public:void use() const override {std::cout Using ConcreteProductB std::endl;}
};// 工厂类
class Factory {
public:virtual Product* createProduct() const 0;Product* getProduct() const {Product* product createProduct();// 可以在这里添加其他的初始化逻辑return product;}
};// 具体工厂类 A
class ConcreteFactoryA : public Factory {
public:Product* createProduct() const override {return new ConcreteProductA();}
};// 具体工厂类 B
class ConcreteFactoryB : public Factory {
public:Product* createProduct() const override {return new ConcreteProductB();}
};int main() {Factory* factory nullptr;Product* product nullptr;std::string choice;std::cout Enter A for ConcreteProductA, B for ConcreteProductB: ;std::cin choice;// 根据用户的选择实例化不同的具体工厂类if (choice A) {factory new ConcreteFactoryA();} else if (choice B) {factory new ConcreteFactoryB();} else {std::cout Invalid choice std::endl;return 0;}// 使用工厂类创建产品对象product factory-getProduct();product-use();delete factory;delete product;return 0;
} AbstactFactory 模式 产品对象家族
假如我们要买水果水果的产地来自中国、日本、美国每个国家的水果种类都可以分为苹果、香蕉、梨子。作为开发者我们就不得不创建苹果类香蕉和梨子类似然后每种苹果都继承自苹果类。每上架一个国家的苹果我们都要实现一次苹果类这样就会有成千上万的苹果类需要被创建AbstractFactory 模式就是用来解决这类问题的要创建一组相关或者相互依赖的对象。 //抽象工厂模式
#include iostream
using namespace std;//苹果的抽象
class AbstractApple {
public:virtual void showName() 0;
};//中国苹果
class ChinaApple :public AbstractApple {
public:virtual void showName() {cout 中国苹果 endl;}
};//美国苹果
class USAApple :public AbstractApple {
public:virtual void showName() {cout 美国苹果 endl;}
};//日本苹果
class JapanApple :public AbstractApple {
public:virtual void showName() {cout 日本苹果 endl;}
};//香蕉的抽象
class AbstractBanana {
public:virtual void showName() 0;
};//中国香蕉
class ChinaBanana :public AbstractBanana {
public:virtual void showName() {cout 中国香蕉 endl;}
};//美国香蕉
class USABanana :public AbstractBanana {
public:virtual void showName() {cout 美国香蕉 endl;}
};//日本香蕉
class JapanBanana :public AbstractBanana {
public:virtual void showName() {cout 日本香蕉 endl;}
};//鸭梨的抽象
class AbstractPear {
public:virtual void showName() 0;
};//中国鸭梨
class ChinaPear :public AbstractPear {
public:virtual void showName() {cout 中国鸭梨 endl;}
};//美国鸭梨
class USAPear :public AbstractPear {
public:virtual void showName() {cout 美国鸭梨 endl;}
};//日本鸭梨
class JapanPear :public AbstractPear {
public:virtual void showName() {cout 日本鸭梨 endl;}
};//抽象工厂 针对产品族
class AbstractFactory {
public:virtual AbstractApple* CreateApple() 0;virtual AbstractBanana* CreateBanana() 0;virtual AbstractPear* CreatePear() 0;
};//中国工厂
class ChinaFactory :public AbstractFactory {virtual AbstractApple* CreateApple() {return new ChinaApple;}virtual AbstractBanana* CreateBanana() {return new ChinaBanana;}virtual AbstractPear* CreatePear() {return new ChinaPear;}
};//美国工厂
class USAFactory :public AbstractFactory {virtual AbstractApple* CreateApple() {return new USAApple;}virtual AbstractBanana* CreateBanana() {return new USABanana;}virtual AbstractPear* CreatePear() {return new USAPear;}
};//日本工厂
class JapanFactory :public AbstractFactory {virtual AbstractApple* CreateApple() {return new JapanApple;}virtual AbstractBanana* CreateBanana() {return new JapanBanana;}virtual AbstractPear* CreatePear() {return new JapanPear;}
};void test01() {AbstractFactory* factory NULL;AbstractApple* apple NULL;AbstractBanana* Banana NULL;AbstractPear* Pear NULL;//中国工厂factory new ChinaFactory;apple factory-CreateApple();Banana factory-CreateBanana();Pear factory-CreatePear();apple-showName();Banana-showName();Pear-showName();delete Pear;delete apple;delete Banana;delete factory;
}int main()
{test01();
}
Singleton 模式 单例模式针对一个类的唯一实例 Singleton 模式是设计模式中最为简单、最为常见、最容易实现也是最应该熟悉和掌握的模式。Singleton 模式就是一个类只创建一个唯一的对象即一次创建多次使用。
实现单例模式的步骤1、构造函数私有化2、增加静态私有的当前类的指针变量3、提供静态对外接口,可以让用户获得单例对象
单例分为懒汉式和饿汉式
懒汉式解决了饿汉式内存浪费问题但是线程不安全的可以通过互斥量mutex.lock()和mutex.unlock()来解决懒汉用的比较多饿汉式还没有使用该单例对象该单例对象就已经被加载到内存了在对象过多时会造成内存浪费饿汉模式会在程序启动时就创建单例对象并且该对象会一直存在于内存中即使在程序执行过程中没有被使用。这可能会导致内存浪费特别是在单例对象比较大或者创建单例对象需要消耗大量资源的情况下。
这个是饿汉模式返回的是一个静态变量静态变量没运行就会产生数据
class Singleton {
private:static Singleton instance;Singleton() {}public:static Singleton getInstance() {return instance;}void doSomething() {std::cout Singleton instance is doing something. std::endl;}
};Singleton Singleton::instance;int main() {Singleton singleton Singleton::getInstance();singleton.doSomething();return 0;
}
这个是懒汉模式返回的是一个静态变量指针程序调用getinstance才会产生数据
#include iostream
#include mutexclass Singleton {
private://类外定义成员变量static Singleton* instance;static std::mutex mutex;//构造函数私有化Singleton() {}public:static Singleton* getInstance() {if (instance nullptr) {std::lock_guardstd::mutex lock(mutex);if (instance nullptr) {instance new Singleton();}}return instance;}void doSomething() {std::cout Singleton instance is doing something. std::endl;}
};Singleton* Singleton::instance nullptr;
std::mutex Singleton::mutex;int main() {Singleton* singleton Singleton::getInstance();singleton-doSomething();return 0;
}