C#基础-面向对象详解
面向对象详解
一.什么是面向对象
1>面向对象是一种程序设计思想
2>面向过程和面向对象是什么?
例如要把大象放冰箱怎么做?
面向过程:打开冰箱门->把大象扔进去->关上冰箱门(如下图)
面向对象:两个对象,大象和冰箱。大象有自己的固有属性高和重量,还有两个动作分别是进冰箱和出冰箱。冰箱也有自己固有属性高和重量,动作也有开门和关门
区分:
1.面向过程是解决问题的常规思路,更加符合解决问题的想法,但是随着步骤越来越多,就很难满足需求了。
2.面向对象是把东西分拆为各个对象,每个对象完成自己的核心动作,分工合作,对象之间交互完成功能。
二.面向对象的三大特性
1.封装
下面几行代码,就是封装一个对象,描述的是一只大象,大象有一些特性(身高和重量)和行为(进冰箱或出冰箱)
1 public class Elephant 2 { 3 public int Height = 0; 4 public int Weigth = 0; 5 public void IntoFridge() 6 { 7 Console.WriteLine("进冰箱"); 8 } 9 public void OutFridge() 10 { 11 Console.WriteLine("出冰箱"); 12 } 13 }
总结:
1>把数据和行为打包到class中,就叫封装
2>封装的好处有,数据安全,提供重用性,分工合作和方便构建大型复杂的项目
2..继承
下面几行代码,就是实现了继承,大象子类继承了动物父类,其中完全一样的特性(身高,体重)和行为(吃东西)放到父类中,这样做的好处是可以去掉重复代码
大象子类可以拥有动物父类的一切公开的属性和行为,不管大象是否愿意,它都必须拥有父类的公开东西。继承也是实现多态的,接下来会讲到。
1 public class Elephant: Animal 2 { 3 //public int Height = 0; 4 //public int Weigth = 0; 5 public void IntoFridge() 6 { 7 Console.WriteLine("进冰箱"); 8 } 9 public void OutFridge() 10 { 11 Console.WriteLine("出冰箱"); 12 } 13 //public void CanEat() 14 //{ 15 // Console.WriteLine("我可以吃东西"); 16 //} 17 } 18 public class Animal 19 { 20 public int Height = 0; 21 public int Weigth = 0; 22 public void Eat() 23 { 24 Console.WriteLine("我可以吃东西"); 25 } 26 }
3.多态
1>说白了,可以理解为有相同的变量,相同的操作,但是不同的实现
2>多态种类包括:方法的重载;接口&&实现;抽象&&实现 ;继承
例如下图:都是实例化的Animal,都是调用的Eat方法,一个执行的是大象的吃方法,一个执行的是人的吃方法,这就可以理解为相同的变量,相同的操作,实现方式不同,这就是多态啦!是运行时多态(程序运行时,实现的多态)
1 using System; 2 3 namespace _002_Attribute 4 { 5 class Program 6 { 7 static void Main(string[] args) 8 { 9 Animal animal = new Elephant(); 10 animal.Eat(); 11 Animal animal1 = new People(); 12 animal1.Eat(); 13 Console.Read(); 14 } 15 } 16 public class Elephant : Animal 17 { 18 public void IntoFridge() 19 { 20 Console.WriteLine("进冰箱"); 21 } 22 public void OutFridge() 23 { 24 Console.WriteLine("出冰箱"); 25 } 26 public override void Eat() 27 { 28 Console.WriteLine("我是大象,我吃植物"); 29 } 30 } 31 public class People : Animal 32 { 33 public override void Eat() 34 { 35 Console.WriteLine("我是人,我吃米饭"); 36 } 37 } 38 public abstract class Animal 39 { 40 public int Height = 0; 41 public int Weigth = 0; 42 public abstract void Eat();//抽象方法,必须在抽象类中 43 } 44 }
4.抽象
面向对象说是有封装,继承,多态三大特性,也可以说成有四大特性,包括抽象,抽象也是很常见的。
1>抽象方法:子类都得有,实现方式不同,此时考虑用抽象方法。这里注意,抽象方法必须在抽象类中
1>抽象类:
首先抽象类是父类,里面放得都是共有的东西;
抽象类中有约束(抽象方法);
抽象类是不能实例化,只能由实现抽象了的子类去实例化
抽象类中,放的都是共有的东西
三.怎么选择抽象类和接口(重点)
接口:约束
1>只能约束
2>特点是,多实现,更加灵活
3>语义方面有点像:can do,可以说“实现接口的子类 can do 接口约束”
4>有的子类有,有的子类没有的情况,就要考虑用接口
抽象类:父类+约束
1>可完成通用的实现,只能单继承
2>语义方面有点像: is a,可以说“子类is a 父类”
选择接口还是抽象类的原则:子类都一样的,放在父类;子类都有但是不同,放在父类抽象一下;有的子类有,有的子类没有,那就用接口
一般情况,接口用的更多,因为接口更简单灵活 除非有些共有的需要继承,下面是一个小例子:
需求:门,有材质,猫眼,门铃,开门(),关门(),烟雾报警();等。
请问:用面向对象的程序设计思想,怎么去封装??(值得深思,希望能起到与一反三的效果)
1 interface IExtend 2 { 3 string CatEye { get; set; }//猫眼 4 string Doorbell { get; set; }//门铃 5 void SmokeAlarm();//烟雾报警 6 7 } 8 public abstract class BaseDoor 9 { 10 public string RawStock { get; set; }//材料 11 12 //以下两个开门和关门在父类用抽象,因为开关门的方式会有不同,有些门自动开关,有些需要人去开关 13 public abstract void Open();//开门 14 public abstract void Close();//关门 15 }
四.抽象方法和虚方法的区别
1>最本质的区别:虚方法带有实现(方法体),可以被重载;抽象方法没有实现
2>下面的例子,详细说明了抽象方法和虚方法的用法,程序中做了很详细的注释,程序运行结果如下图:
1 using System; 2 3 namespace _002_Attribute 4 { 5 class Program 6 { 7 static void Main(string[] args) 8 { 9 //虚方法/抽象方法,程序编译时候,左边遇到virtual/abstract时,做个标记,等程序运行的时候,判断右边是否有override,如果有,就以右边为准 10 11 ParentClass parent = new Child(); 12 parent.CommonMethod();//普通方法,父类为准;这个是编译时确定的,特点是:效率高 13 parent.VirtualMethod1();//虚方法,子类没重载,左边为准 14 parent.VirtualMethod2();//虚方法,子类有重载,右边为准;运行时确定,特点是为了灵活 15 parent.AbstractMethod();//抽象方法,右边为准;运行时确定,特点是为了灵活 16 Console.Read(); 17 } 18 } 19 public class Child : ParentClass 20 { 21 public override void VirtualMethod2()//子类重载了父类的 VirtualMethod2 22 { 23 Console.WriteLine("我是子类,重载虚方法2"); 24 } 25 public override void AbstractMethod() 26 { 27 Console.WriteLine("我是子类,实现后的抽象方法"); 28 } 29 } 30 public abstract class ParentClass 31 { 32 /// <summary> 33 /// 普通父类方法 34 /// </summary> 35 public void CommonMethod() 36 { 37 Console.WriteLine("我是父类,普通方法"); 38 } 39 /// <summary> 40 /// 父类虚方法,必须包含实现,可以被重载 41 /// </summary> 42 public virtual void VirtualMethod1() 43 { 44 Console.WriteLine("我是父类,虚方法1"); 45 } 46 public virtual void VirtualMethod2() 47 { 48 Console.WriteLine("我是父类,虚方法2"); 49 } 50 /// <summary> 51 /// 我是抽象方法 52 /// </summary> 53 public abstract void AbstractMethod(); 54 } 55 56 }