码迷,mamicode.com
首页 > 编程语言 > 详细

《21天C++》笔记之6月27日

时间:2017-06-27 20:50:29      阅读:223      评论:0      收藏:0      [点我收藏+]

标签:纯虚函数   不能   public   使用   转换   派生   引用   资源   des   

继承

  • 公有继承,is-a的关系,比如,He is a man;

    派生类可访问基类非私有成员,派生类实例也是;

  • 私有继承和保护继承,has-a的关系,Car has a motor;

    私有继承,也让派生类可访问基类非私有成员,但派生类实例无法访问基类任何成员,并且派生类的的子类也无法访问基类任何成员;

    保护继承,与私有继承不同的是,子类的子类是可以访问基类的非私有成员;

注意:仅当必要时才使用私有或保护继承,遇到has-a情况时,尽量用组合或者聚合的方式替代(即将‘基类对象当作‘子类’‘的一个成员属性)

class Motor
{
public:
	void SwitchIgnition();
	void PumpFuel();
	void FireCylinders();
};
class Car
{
private:
	Motor heartOfCar;
public:
	void Move()
	{
		heartOfCar.FireCylinders();
		heartOfCar.PumpFuel();
		heartOfCar.SwitchIgnition();
	}
};
  • 切除:将子类对象显示复制给父类对象,或通过参数传递给父类对象,会只保留Base部分,这叫做切除
class Platypus:public Mammal,public Reptile,public Bird{};//多继承
  • 重载,覆盖,隐藏:重载就是一个类里同名不同参数的函数,覆盖就是子类与父类同名同参数的函数,隐藏就是子类会将父类中同名但不同参数的函数隐藏,即实例不能访问。

多态

  • 使用虚函数实现多态行为,通过引用或者指针调用虚函数即可实现多态

  将派生类对象视为基类对象,并执行派生类的覆盖函数

class Fish
{
public:
    virtual void Swim()
    {
        cout << "Fish Swim.." << endl;
    }
};

class Tuna : public Fish
{
public:
    virtual void Swim()
    {
        cout << "Tuna is fast" << endl;
    }
};

class Carp : public Fish
{
public:
    virtual void Swim()
    {
        cout << "Carp is slow" << endl;
    }
};
int main()
{
    Tuna t;
    Carp c;
    Fish &f1 = t;
    f1.Swim();
    return 0;
}
  • 对于使用new在自由存储区中实例化派生类对象,如果将其付给基类指针,
  • 并通过该指针调用delete,将不会调用派生类的析构函数.
  • 这可能会导致资源未释放,内存泄露等问题.
  • 要避免这种问题,要将析构函数声明为虚函数.
class Fish
{
public:
    Fish()
    {
        cout <<"Constructed Fish"<< endl;
    }
    ~Fish()
    {
        cout << "Destroyed Fish" << endl;
    }
};

class Tuna : public Fish
{
public:
    Tuna()
    {
        cout << "Constructed Tuna" <<endl;
    }
    ~Tuna()
    {
        cout << "Destroyed Tuna" << endl;
    }
};

void DeleteFishMemory(Fish *pFish)
{
    delete pFish;
}

int main()
{
    Tuna *pTuna = new Tuna;
    DeleteFishMemory(pTuna);
    return 0;
}
/*输出:
**Constructed Fish
**Constructed Tuna
**Destroyed Fish
*/

抽象基类与纯虚函数

  不能被实例化的基类称为抽象基类,可通过声明纯虚函数创建.

class Fish
{
public:
	virtual void Swim() = 0;
};

class Tuna : public Fish
{
public:
	void Swim()
	{
		cout << "Tuna swims fast in the sea " << endl;
	}
};

使用虚继承解决菱形问题,(二义性)

    

class Animal
{
public:
    Animal()
    {
        cout << "ANimal constructor" << endl;
    }

    int Age;
};

class Mammal:public virtual Animal
{

};

class Bird:public virtual Animal
{};

class Reptile:public virtual Animal
{};

class Platypus:public Mammal, public Bird, public Reptile
{
public:
    Platypus()
    {
        cout << "Platypus constructor" <<endl;
    }
};

int main()
{
    Platypus duckBilledp;

    duckBilledp.Age = 25;
    return 0;
}

 

  • 继承多个从同一个类派生而来的基类时,如果没有使用虚继承,将会继承多个基类的父类,而使用了虚继承,则只继承一个.
  • virtual关键字有两个不同概念,一个是用于多态,另一个是用于虚继承解决二义性

 

从技术上说,C++不支持虚复制构造函数

运算符类型与运算符重载

  • 单目运算符

    1, (++)递增运算符

      Date operator ++ (){} 单目前缀运算符在类中重载

      Date operator ++ (int){}单目后缀运算符在类中重载

    2, 转换运算符,下例是用转换运算符将Date转换为const char*

 

class Date
{
private:
    int Day;
    int Month;
    int Year;

    string DateInString;
public:
    Date (int InputDay, int InputMonth, int InputYear) : Day(InputDay), Month(InputMonth), Year(InputYear)
    {}

    operator const char*()
    {
        ostringstream formattedDate;
        formattedDate << Day << " / " << Month << " / " << Year;

        DateInString = formattedDate.str();
        return DateInString.c_str();
    }
};

int main()
{
    Date Holiday (25, 12, 2011);
    cout << "Holiday is on: " << Holiday << endl;
    return 0;
}
//结果:Holiday is on: 25 / 12 / 2011

 

《21天C++》笔记之6月27日

标签:纯虚函数   不能   public   使用   转换   派生   引用   资源   des   

原文地址:http://www.cnblogs.com/qiuxd/p/7086886.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!