关于c++:打造可复用的数据结构库2-异常类族的构建

10次阅读

共计 5910 个字符,预计需要花费 15 分钟才能阅读完成。

1 为什么有异样类族

​ 在程序的逻辑解决的时候,会有一些异样的景象,这种状况,咱们只能预测他可能呈现,然而却无奈彻底的防止,则就要在一些会出现异常的中央做些进攻,一旦出现异常,就要有相应的解决对策。

2 异样类的构建

​ 一个工程中,代码的逻辑是盘根错节,则就要有肯定的章程来治理异样的解决,这样,能够帮忙咱们的程序看起来洁净整洁。在当初的工程中,常见的异样个别有:

  1. 计算异样;例如做了除以 0 的操作
  2. 空指针异样:例如对空指针做了不非法的操作
  3. 拜访越界异样
  4. 内存不足异样
  5. 参数谬误异样

​ 异常情况的整顿与分类,咱们能够看出,这些异样有肯定的共性,但也有不同的中央。咱们就利用 C ++ 语言语言的继承与多态的个性,做一个根底的异样类,而后各个类从根底类继承,而后本人增加本人的个性。

2.1 异样类的基类构建

2.1.1 提醒函数

​ 既然是异样的类,他的呈现,就是为了告警,那么就会有一些提示信息,理论应用的应用,都是抛出异样的中央输出一些提醒语句。那么构建类的时候,就要设计提醒语句的输出的中央。

Exceptional(const char *message);
Exceptional(const char *file, int line);
Exceptional(const  char *message, const char *file,const int line);

virtual const char *message() const;
virtual const char * location() const ;

​ 从这三个构建函数的样子能够看出,根本是一样的,就是个别的参数没有而已,为了代码的复用,能够写一个专用的公有函数来做三个构建函数的实现。

 void init(const char *message, const char *file, int line);
2.1.2 属性工能函数

​ 既然是类,就要合乎 C ++ 的类的个别共性,然而该类在 赋值操作的时候,或者拷贝结构的时候,就须要非凡解决,则须要对这两个工能做解决

Exceptional(const Exceptional&  obj);
Exceptional& operator = (const  Exceptional& obj);

2.2 类的架构

​ 以上的形容曾经根本能够结构这个类了,然而有个细节要留神,就是在传入的字符串存储空间是无奈确定的。为了避免意外,该类要对传入的字符串做一个复制,在函数被析构的时候,就要开释。所以类的结构如下。

    class Exceptional
    {
    protected:
        char* m_message=nullptr;
        char* m_location =nullptr;
        
        void init(const char *message, const char *file, int line);
    public:
        Exceptional(const char *message);
        Exceptional(const char *file, int line);
        Exceptional(const  char *message, const char *file,const int line);

        Exceptional(const Exceptional&  obj);
        Exceptional& operator = (const  Exceptional& obj);

        virtual const char *message() const;
        virtual const char * location( ) const ;

        virtual  ~Exceptional() =0 ;};

3 基类的实现

     void Exceptional :: init(const char *message, const char *file, const int line)
     {
         // 因为不能保障传进来的 message 的空间,所以复制一份存到堆中
         m_message= strdup(message);

         if(file != NULL)
         {char sl[16]={0};
             itoa(line,sl,10);
             m_location=reinterpret_cast<  char *  >(malloc( strlen( file) +strlen(sl)+2  ) ) ;

             m_location = strcpy(m_location,file);
             m_location = strcat (m_location ,";");
             m_location = strcat (m_location ,sl);

         }
         else
         {m_location=nullptr;}
     }

    Exceptional :: Exceptional(const char *message)
    {init( message, NULL, NULL);
    }

    Exceptional :: Exceptional(const char *file, int line)
    {init( NULL, file, line);
    }

    Exceptional :: Exceptional(const char *message, const char *file,const int line)
    {init( message, file, line);
    }


    Exceptional :: Exceptional(const Exceptional&  obj)
    {m_message= strdup(obj.m_message);
        m_location= strdup(obj.m_location);
    }

    Exceptional& Exceptional :: operator = (const  Exceptional& obj)
    {if(this != &obj)
        {free(m_message);
            free(m_location);

            m_message= strdup(obj.m_message);
            m_location= strdup(obj.m_location);
        }

        return *this;
    }


    const char * Exceptional :: message() const
    {return m_message;}

    const char * Exceptional :: location( ) const
    {return m_location;}


    Exceptional ::  ~Exceptional()
    {free(m_message);
        free(m_location);
    }

4 继承类的实现

基类实现当前,剩下的就是对各自类的具体实现、

4.1 计算异样类的实现

    /****************************************************
     *  class ArithmeticExcption  计算异样
     ****************************************************
     * */
    class ArithmeticExcption :public Exceptional
    {
    public:
        ArithmeticExcption() : Exceptional(nullptr) {}
        ArithmeticExcption(const char  * message) : Exceptional(message) {}
        ArithmeticExcption(const char *file, int line): Exceptional(file, line) {}
        ArithmeticExcption(const  char *message, const char *file,const int line):Exceptional(message, file, line){}

        ArithmeticExcption(const  ArithmeticExcption & obj) : Exceptional(obj){}

        ArithmeticExcption& operator = (const ArithmeticExcption & obj)
        {Exceptional::operator = ( obj);
            return *this ;
        }
    };

4.2 空指针异样

    /****************************************************
     *  class NullPointerExcption   空指针异样
     ****************************************************
     * */
    class NullPointerExcption :public Exceptional
    {
    public:
        NullPointerExcption() : Exceptional(nullptr) {}
        NullPointerExcption(const char  * message) : Exceptional(message) {}
        NullPointerExcption(const char *file, int line): Exceptional(file, line) {}
        NullPointerExcption(const  char *message, const char *file,const int line):Exceptional(message, file, line){}

        NullPointerExcption(const  NullPointerExcption & obj) : Exceptional(obj){}

        NullPointerExcption& operator = (const NullPointerExcption & obj)
        {Exceptional::operator = ( obj);
            return *this ;
        }
    };

4.3 拜访越界异样

    /****************************************************
     *  class IndexOutOfBoundsException   拜访越界异样
     ****************************************************
     * */
    class IndexOutOfBoundsException :public Exceptional
    {
    public:
        IndexOutOfBoundsException() : Exceptional(nullptr) {}
        IndexOutOfBoundsException(const char  * message) : Exceptional(message) {}
        IndexOutOfBoundsException(const char *file, int line): Exceptional(file, line) {}
        IndexOutOfBoundsException(const  char *message, const char *file,const int line):Exceptional(message, file, line){}

        IndexOutOfBoundsException(const  IndexOutOfBoundsException & obj) : Exceptional(obj){}

        IndexOutOfBoundsException& operator = (const IndexOutOfBoundsException & obj)
        {Exceptional::operator = ( obj);
            return *this ;
        }
    };

4.4 内存不足异样

    /****************************************************
     *  class NoEnoughMemoryException   内存不足异样
     ****************************************************
     * */
    class NoEnoughMemoryException :public Exceptional
    {
    public:
        NoEnoughMemoryException() : Exceptional(nullptr) {}
        NoEnoughMemoryException(const char  * message) : Exceptional(message) {}
        NoEnoughMemoryException(const char *file, int line): Exceptional(file, line) {}
        NoEnoughMemoryException(const  char *message, const char *file,const int line):Exceptional(message, file, line){}

        NoEnoughMemoryException(const  NoEnoughMemoryException & obj) : Exceptional(obj){}

        NoEnoughMemoryException& operator = (const NoEnoughMemoryException & obj)
        {Exceptional::operator = ( obj);
            return *this ;
        }
    };

4.5 参数异样

    /****************************************************
     *  class InvalidParameterExcetion   参数异样
     ****************************************************
     * */
    class InvalidParameterExcetion :public Exceptional
    {
    public:
        InvalidParameterExcetion() : Exceptional(nullptr) {}
        InvalidParameterExcetion(const char  * message) : Exceptional(message) {}
        InvalidParameterExcetion(const char *file, int line): Exceptional(file, line) {}
        InvalidParameterExcetion(const  char *message, const char *file,const int line):Exceptional(message, file, line){}

        InvalidParameterExcetion(const  InvalidParameterExcetion & obj) : Exceptional(obj){}

        InvalidParameterExcetion& operator = (const InvalidParameterExcetion & obj)
        {Exceptional::operator = ( obj);
            return *this ;
        }
    };

5 应用留神

类的父子兼容性准则,做 catch 时,把子类写在前边。

正文完
 0