C#面向对象五(继承、抽象类和抽象方法、多态、虚方法、IS、AS、NEW覆盖关键字)

1.继承的特点:

继承顺序的不可逆性:继承是从上往下依此继承,而不能逆序进行。

继承的延续性:在继承顺序中,下一级具备上一级的属性和特征。

2.继承的好处:

代码复用,避免重复。

一处更新,处处更新。

3.继承的步骤和使用要点:

抽取公共部分,放到一个特定的类中(父类)。

其他类(子类)只需要继承父类,即可拥有父类特征(属性和方法)。

根据子类的需要添加属于自己的特征和方法。

4.继承的实现(和接口的实现形式类似)

在子类后面使用冒号“:”继承父类,如 class Dog : Animal

5.概念解释

子类继承父类,父类派生子类。

子类又叫派生类,父类又叫基类(超类)。

子类继承父类成员,也可以有自己独立的成员。

6.继承的条件

继承需要符合的关系:is-a 的关系  Cat is an Animal。

7.继承中的构造函数

this:可以使用this关键字访问父类成员(在构造函数中)。

base:调用父类的构造函数、调用父类的属性和方法。

继承中使用base关键字

public Dog(string name,string color,string kind,string favorite):base(name,color,kind)
{
     this.Favorite=favorite;  
}

继承中base关键字(2)

class Animal
    {
        //父类构造函数
        public Animal() { }
        public Animal(string name, string color, string kind)
        {
            this.Color = color;
            this.Name = name;
            this.Kind = kind;
        }
       
        public string Name { get; set; }//名字
        public string Color { get; set; }//颜色
        public string Kind { get; set; }//种类
        public string Favorite { get; set; }//喜好
    }

class Dog : Animal
    {     
        public Dog(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }          
    }
8.protected关键字

protected访问修饰符允许子类访问,而不允许其他非子类访问。

修饰符 类内部 子类 其他类
public 可以 可以 可以
private 可以 不可以 不可以
protected 可以 可以 不可以

9.子类调用父类构造函数总结

隐式调用:如果其他子类的构造函数没有使用base指明调用父类哪个构造函数时,子类会默认调用父类的无参构造函数:base()。这时父类要提供无参的构造函数。

显式调用:如果父类没有无参的构造函数,子类构造函数必须指明调用父类哪个构造函数。

10.继承的特性

继承的传递性:传递机制 A——>B   B——>C   C具有A的特性

继承的单根性:一个类只能有一个父类

例如机器视觉技术与软件学科又属于光学学科,能否同时继承两种人?  答案:不能

11.抽象类和抽象方法 abstract override

抽象方法就是在父类中未实现的方法,在子类中必须实现父类中的所有的抽象方法。

一个抽象类内可以没有抽象方法。

一个抽象方法所在的类必须是抽象类。

抽象方法和重写

abstract class Animal
{
   public string Name {get;set;}
   public Animal(){}
   //用abstract修饰抽象方法
   public abstract void Have();
}

class Dog:Animal
{
   //用override重写父类未实现的方法
   public override void Have()
   {
       Console.WriteLine("狗吃骨头");
   }
}

class Cat:Anima
{
    public override void Have()
    {
        Console.WriteLine("猫吃鱼");
    }
}    

抽象方法和重写(2)

abstract class Animal
    {
        public string Name { get; set; }//名字
        public string Color { get; set; }//颜色
        public string Kind { get; set; }//种类
        public string Favorite { get; set; }//喜好
        //父类构造函数
        public Animal() { }
        public Animal(string name, string color, string kind)
        {
            this.Color = color;
            this.Name = name;
            this.Kind = kind;
        }
        //抽象方法
        public abstract void Have();
    }

class Dog : Animal
    {
        public Dog(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
        public override void Have()
        {
            Console.WriteLine("我们要吃香喷喷的排骨啦!");
        }
    }

class Cat : Animal
    {
        public Cat(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
        public override void Have()
        {
            Console.WriteLine("我们要吃香喷喷的烤鱼啦!");
        }
    }

static void Main(string[] args)
        {
            //创建一只狗和一只猫
            Cat objCat = new Cat("球球儿", "黄色", "小花猫", "小鱼");
            Dog objDog = new Dog("棒棒", "黑色", "小黑狗", "排骨");
            //将子类对象添加的父类集合
            List<Animal> list = new List<Animal>();
            list.Add(objCat);
            list.Add(objDog);
            //取出子类对象
            foreach (Animal obj in list)
            {
                obj.Have();//***********这就是多态***********
            }
            Console.ReadLine();
        }
12.抽象类的概念与使用要点

12.1使用关键字abstract修饰的类,称为抽象类

12.2抽象类只是用来列举一个类所具有的行为,不能单独通过创建对象来使用,也就是说抽样类不能被new

12.3抽象类中可以有抽象方法,也可以没有任何抽象方法

12.4抽象类不能是静态的(static)或密封的(sealed),密封类不能被继承

13.抽象方法的概念与使用要点

13.1在抽象类中使用abstract修饰的方法,沉稳给抽象方法

13.2抽象方法必须在抽象类中定义,不能在普通类中使用

13.3抽象方法只是一个方法的声明,不能有任何方法体

13.4抽象方法仅仅是表示一个应该具有的行为,具体实现由其子类实现

13.5抽象方法在子类中被实现(重写)必须使用关键字override

13.6子类必须重写父类的所有抽象方法,除非子类本身也是抽象类

14.多态

概念:不同对象,接受相同信息,产生不同行为,称为多态。

多态是由“聪明的”虚拟机自行决定的。

例如:子类重写了父类的抽象方法,父类集合中的对象直接调用抽象方法,实现子类中重写的抽象方法,可以称之为多态。

15.使用继承实现多态

15.1父类中必须由抽象方法和虚方法

15.2子类必须重写父类中的抽象方法或虚方法

15.3子类对象必须转换成父类类型去使用

多态的应用大大提高了程序的可扩展性

abstract class Animal
    {
        public string Name { get; set; }//名字
        public string Color { get; set; }//颜色
        public string Kind { get; set; }//种类
        public string Favorite { get; set; }//喜好
        //父类构造函数
        public Animal() { }
        public Animal(string name, string color, string kind)
        {
            this.Color = color;
            this.Name = name;
            this.Kind = kind;
        }
        //抽象方法
        public abstract void Have();
    }

class Dog : Animal
    {
        public Dog(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
        //吃饭
        public override void Have()
        {
            Console.WriteLine("我们要吃香喷喷的排骨啦!");
        }
    }

class Cat : Animal
    {
        public Cat(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
        //吃饭
        public override void Have()
        {
            Console.WriteLine("我们要吃香喷喷的烤鱼啦!");
        }
    }

static void Main(string[] args)
        {
            //创建一只狗和一只猫
            Cat objCat = new Cat("球球儿", "白色", "小花猫", "小鱼");
            Dog objDog = new Dog("棒棒", "黑色", "小黑狗", "排骨");
            //调用方法,传递子类对象
            Test(objCat);
            Test(objDog);
            Console.ReadLine();
        }
继承多态的典型应用
16.里氏替换原则

16.1子类的对象能够替换父类

16.2父类对象不能够替换子类

16.3父类的方法都要在子类中实现或重写

解释:父类的范围广,父类包含子类,狗类属于动物类,但动物类不能仅属于狗类

17.is和as操作符

is操作符检查是否与指定类型兼容。如果转换失败程序中断

foreach (Animal obj in list)
{
   if(obj is Cat)
        Console.WriteLine("我是只猫");
   else if (obj is Dog)
        Console.WriteLine("我是条狗");
}    
 is操作符    

as操作符用于在兼容的引用类型之间执行转换,转换失败返回null

Cat cat = obj as Cat;

18.引入虚方法(虚方法和抽象方法的区别)

18.1抽象方法的特点:抽象方法仅仅是声明,没有任何实现内容;抽象方法一般必须在子类中被重写以后才有使用价值。

18.2如果父类中提供一个方法,要求由自己的方法体,子类根据自己的需要再决定是否需要重写此方法,该如何实现?————>>>>>>虚方法! 原来的abstract换成virtual。

18.3如果子类重写了虚方法,调用的就是子类的;如果子类未重写虚方法,调用的就是父类的。

虚方法

19.虚方法与抽象方法比较

虚方法 抽象方法
用virtual修饰 用abstract修饰
要有方法体,哪怕是一个分号 不允许有方法体
可以被子类override   必须被子类override
除了密封类都可以写 必须在抽象类中

20.object类自带的虚方法

Eauals()虚方法

对于字符串和值类型,能够自动比较是否相等

对于对象比较,必须重写override后才有意义

ToString()虚方法

对于值类型,返回变量值的字符串表示

对于对象,默认返回该对象的完全限定类型名(完全限定类型名:引用空间+类名),可根据需要重写

21.密封类sealed

当一个类使用sealed修饰后,该类不能被继承。

sealed对于保护知识产权起到一定作用,一定程度限制别人二次开发。

22.方法覆盖new

子类中的方法定义时使用new关键字覆盖父类中的同名方法

使用子类覆盖父类的方法后,子类对象调用该方法调用的是子类中new的方法

如果其他子类没有覆盖new父类的同名方法,其他子类对象调用此方法时仍然是父类中的方法

在控件开发中经常使用new关键字来覆盖父类的同名方法

//Dog覆盖了Introduce(),Cat未处理
abstract class Animal
    {
        public string Name { get; set; }//名字
        public string Color { get; set; }//颜色
        public string Kind { get; set; }//种类
        public string Favorite { get; set; }//喜好
        //父类构造函数
        public Animal() { }
        public Animal(string name, string color, string kind)
        {
            this.Color = color;
            this.Name = name;
            this.Kind = kind;
        }       
        //自我介绍
        public void Introduce()
        {
            string info = string.Format("这是父类的方法,我是漂亮的{0},我的名字叫{1},身穿{2}的衣服,我爱吃{3}!",
                 Kind, Name, Color, Favorite);
            Console.WriteLine(info);
        }       
    }

class Dog : Animal
    {
        public Dog(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
        public new void Introduce()
        {
            string info = string.Format("这是Dog类中的方法Hi! I am {0},My Name is {1}!",
                Kind, Name);
            Console.WriteLine(info);          
        }
    }

class Cat : Animal
    {
        public Cat(string name, string color, string kind, string favorite)
            : base(name, color, kind)
        {
            this.Favorite = favorite;
        }
    }

static void Main(string[] args)
        {
            //创建一只狗和一只猫
            Cat objCat = new Cat("球球儿", "黄色", "小花猫", "小鱼");
            objCat.Introduce();
            Dog objDog = new Dog("棒棒", "黑色", "小黑狗", "排骨");
            objDog.Introduce();
            Console.ReadLine();
        }

使用new覆盖掉父类中的方法
23.面向对象三大特性简单总结

23.1封装  隐藏内部实现,稳定外部接口——>系统稳定性

23.2继承  子类继承父类成员,实现代码复用——>开发和维护效率

23.3多态  不同子类,对同一消息,做出不同反应——>系统扩展性

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值