A factory that implements automatic registration in C ++

Source: Internet
Author: User
Tags case statement map data structure

A factory that implements automatic registration in C ++

I haven't updated my blog for a long time. It's not because the blogger is not lazy. It's because the blogger is helping graduate students get master's thesis, positioning, imu, pedestrian track, laser match, and abuse, all are tears.

Factory mode. You can create a derived class instance in the project. Generally, switch-case is used internally to create different derived class objects based on different keys.

switch(Key) {    case A:         return new A;    case B:        return new B;    ...}

For a simple inheritance system, this is also acceptable. For a complex system, such as a command system, there are at last more than 100 business commands, then, do you want to write the switch-case statement as long as the cloth of the lazy mother-in-law? Obviously, this is not acceptable. Today we will implement an automatic registration factory.
In fact, I have read this design idea a long time ago. For the first time, it seems to be a cpp blog, and for the second time it was in csdn. Recently, the cpp community "Zhiyi" saw it again, however, they are just a demo code. Although we only write it in simple mode, we try to make it usable directly.
In fact, the idea is very simple. With the help of the map data structure, the unique ID mark of the class is used as the map key, while the value is a lambda expression, which is used to generate class instances.
The factory Code is as follows:

#ifndef FACTORY#define FACTORY#include 
  
   #include
   #include 
    
     using namespace std;template 
     
      class Factory{public:    typedef T type_value;    template 
      
        struct register_h { register_h(const K& key) { Factory::instance()->m_creators[key] = []{ return new N; }; } }; static auto instance() -> Factory
       
        * { static Factory
        
          f; return &f; } auto creat(const K& key) -> T* { T* re = NULL; auto ite = m_creators.find(key); if (ite != m_creators.end()) { re = (ite->second)(); } return re; } static auto produce(const K& key) -> T* { return Factory::instance()->creat(key); }private: Factory() {} Factory(const Factory&) = delete; Factory(Factory&&) = delete; Factory& operator =(const Factory&) = delete; std::map
         
          > m_creators;};#define CLASS_NAME(CLASS) #CLASS#endif // FACTORY
         
        
       
      
     
    
  

String is used as the key value by default.register_hClass is an important step. We use the group's Instantiation to complete the registration action.
Some other functions are basic functions, which are nothing more than search operations.
Simple use of demo, Object is our base class, and then it has a Widget subclass.

#ifndef OBJECT#define OBJECT#include "factory.h"class Object{public:    virtual ~Object() {}};#define FACTORY_OBJECT Factory#define REGISTER_OBJECT_CLASS_KEY(CLASS, KEY) \    FACTORY_OBJECT::register_h
   
     __##CLASS(KEY)#define REGISTER_OBJECT_CLASS(CLASS) \    REGISTER_OBJECT_CLASS_KEY(CLASS, CLASS_NAME(CLASS))#endif // OBJECT
   
#ifndef WIDGET_H#define WIDGET_H#include "object.h"class Widget : public Object{public:    Widget();};#endif // WIDGET_H
#include "widget.h"Widget::Widget(){}REGISTER_OBJECT_CLASS(Widget);

REGISTER_OBJECT_CLASS(Widget);The Code has been registered, and its instantiation is named_ WidgtOfFactory::register_h Object, which is automatically registered in the constructor.

Main. cpp

#include 
  
   #include "widget.h"using namespace std;int main(){    Widget *p = static_cast
   
    (FACTORY_OBJECT::produce("Widget"));    FACTORY_OBJECT::type_value* p1 = FACTORY_OBJECT::produce("Text");    std::cout << p1;    std::cout << "\n-----------------";    std::cout << p;    std::cout << "Hello World!" << std::endl;    delete p;    delete p1;    return 0;}
   
  

Several Macros in object. h encapsulate the details. However, for example

#ifndef MESSAGE#define MESSAGE#include "factory.h"class Message{};#define FACTORY_MESSAGE Factory
  
   #define REGISTER_MESSAGE_CLASS_KEY(CLASS, KEY) \    FACTORY_MESSAGE::register_h
   
     __##CLASS(KEY)#define REGISTER_MESSAGE_CLASS(CLASS) \    REGISTER_MESSAGE_CLASS_KEY(CLASS, CLASS_NAME(CLASS))#endif // MESSAGE
   
  

A new class inheritance system is written by macros. However, these macro actions are very similar and can be abstracted.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.