zoukankan      html  css  js  c++  java
  • 绝不重新定义继承而来的缺省参数值

    考虑如下的代码:

    class Shape
    {
    public:
        enum ShapeColor{Red, Green, Blue};
        virtual void draw(ShapeColor color = Red) const = 0;
        ...
    };
    
    class Rectangle: public Shape
    {
    public:
        virtual void draw(ShapeColor color = Green) const;
        ...
    };
    
    class Circle: public Shape
    {
    public:
        virtual void draw(ShapeColor color) const;
        ...
    };

    以上代码有个问题,如果你用下面的调用方式:

    Shape *ps;
    Shape *pc = new Circle;
    Shape *pr = new Rectangle;
    
    pc->draw(Shape::Red);    //Circle::draw(Shape::Red);
    pr
    ->draw(Shape::Red);    //Rectangle::draw(Shape::Red); pr->draw();          //Rectangle::(Shape::Red)!!!!

    我们会发现,pr的动态类型是Rectangle*, 所以调用的是Rectangle的virtual函数,Rectangle::draw的缺省参数应该是GREEN,但是,由于pr的静态类型是Shape*,所以此调用的缺省参数值来自Shape而不是Rectangle。C++之所以这么做,是考虑到运行时效率的问题。如果缺省参数值是动态绑定,编译器就必须在运行期为虚函数决定适当的缺省值。这比目前实行的“在编译器决定”机制更慢更复杂。

    那么我们怎么做才适合呢?在派生类里面也提供缺省值吗?

    class Shape
    {
    public:
        enum ShapeColor {Red, Green, Blue};
        virtual void draw(ShapeColor color = Red) const = 0;
        ...
    };
    
    class Rectangle: public Shape
    {
    public:
        virtual void draw(ShapeColor color = Green) const;
        ...
    };

    Aha,代码重复。

    可以用替代设计,比如可以用基类的public 非虚函数调用private的虚函数,后者可以被派生类重新定义,而让非虚函数去做缺省参数的事情。

    class Shape
    {
    public:
        enum ShapeColor { Red, Green, Blue };
        void draw(ShapeColor color = Red) const         //non-virtual
        {
            doDraw(color);
        }
        ...
    private:
        virtual void doDraw(ShapeColor color) const = 0;//do the real work
    };
    
    class Rectangle : public Shape
    {
    public:
        ...
    private:
        virtual void doDraw(ShapeColor color) const;    //不须指定参数值
        ...
    };

    绝对不要重新定义一个继承而来的缺省参数值,这些参数值都是静态的,而虚函数却是动态的。

  • 相关阅读:
    c语言|博客作业05
    C语言I博客作业04
    C语言II博客作业04
    C语言II博客作业03
    C语言II博客作业02
    C语言II博客作业01
    学期总结
    我的第一周C语言作业
    C语言I博客作业08
    C语言I博客作业07
  • 原文地址:https://www.cnblogs.com/edmundli/p/4453581.html
Copyright © 2011-2022 走看看