zoukankan      html  css  js  c++  java
  • C#面向对象之继承

    一、继承

      什么是继承?继承是两个或多个类之间存在的依赖关系,其中被继承的类称为父类或基类,继承的类称为子类或派生类。在继承关系中,父类是对子类的共性提取,子类是对父类的扩展。

     1 /// <summary>
     2 /// 文字
     3 /// </summary>
     4 public class Word
     5 {
     6     /// <summary>
     7     /// 内容
     8     /// </summary>
     9     public string Content { get; set; }
    10     /// <summary>
    11     /// 大小(单位B)
    12     /// </summary>
    13     public int Size { get; set; }
    14 
    15     public Word() { }
    16     public Word(string content, int size)
    17     {
    18         this.Content = content;
    19         this.Size = size;
    20     }
    21 }
    22 /// <summary>
    23 /// 图片
    24 /// </summary>
    25 public class Picture
    26 {
    27     /// <summary>
    28     /// 内容
    29     /// </summary>
    30     public string Content { get; set; }
    31     /// <summary>
    32     /// 大小(单位B)
    33     /// </summary>
    34     public int Size { get; set; }
    35     /// <summary>
    36     /// 地址
    37     /// </summary>
    38     public string Path { get; set; }
    39 
    40     public Picture() { }
    41     public Picture(string content, int size, string path)
    42     {
    43         this.Content = content;
    44         this.Size = size;
    45         this.Path = path;
    46     }
    47 
    48     /// <summary>
    49     /// 图片存储到文件中,并为Path赋值
    50     /// </summary>
    51     public void StoreToFile()
    52     {
    53 
    54     }
    55 }

    上面设计的文字类和图片类中存在代码冗余,为了去除冗余,我通过提取共性的方式引入了第三个类,并让其他两个类继承它,代码如下:

     1 /// <summary>
     2 /// 信息
     3 /// </summary>
     4 public class Information
     5 {
     6     /// <summary>
     7     /// 内容
     8     /// </summary>
     9     public string Content { get; set; }
    10     /// <summary>
    11     /// 大小(单位B)
    12     /// </summary>
    13     public int Size { get; set; }
    14 
    15     public Information() { }
    16     public Information(string content, int size)
    17     {
    18         this.Content = content;
    19         this.Size = size;
    20     }
    21 }
    22 /// <summary>
    23 /// 文字
    24 /// </summary>
    25 public class Word : Information
    26 {
    27     public Word() { }
    28     public Word(string content, int size)
    29     {
    30         this.Content = content;
    31         this.Size = size;
    32     }
    33 }
    34 /// <summary>
    35 /// 图片
    36 /// </summary>
    37 public class Picture : Information
    38 {
    39     /// <summary>
    40     /// 地址
    41     /// </summary>
    42     public string Path { get; set; }
    43 
    44     public Picture() { }
    45     public Picture(string content, int size, string path)
    46     {
    47         this.Content = content;
    48         this.Size = size;
    49         this.Path = path;
    50     }
    51 
    52     /// <summary>
    53     /// 图片存储到文件中,并为Path赋值
    54     /// </summary>
    55     public void StoreToFile()
    56     {
    57 
    58     }
    59 }
    60 /// <summary>
    61 /// 实现对象
    62 /// </summary>
    63 public class RealizeObject
    64 {
    65     public void Realize()
    66     {
    67         //Word类和Picture类继承Information类后,Information类的Content和Size属性就像Word类和Picture类的属性一样
    68         Word word = new Word("book", 4);
    69         Picture picture = new Picture("", 0, @"C:UsersImages");
    70         Information info = new Information("this is Info", 12);
    71     }
    72 }

    通过继承连接文字/图片类和它们提取共性的信息类,实现了代码的复用性,后期如果加上音频类和视频类也可以通过继承复用信息类的代码,而不用重复编写Content和Size属性。

    继承的规则:

    1、子类可以继承除了父类构造函数之外的所有非私有成员。

    2、子类的任意构造函数调用之前会先调用父类的默认构造函数。

    3、子类的可访问性不能高于父类,因为这样会强制父类的可访问性同子类的可访问性(比如Word用public修饰,Information用internal修饰)。

    4、C#不允许类的多重继承,即一个类只能有一个直接父类(继承引号符后面只能写一个类)。

    根据继承规则二,总结继承中代码的执行顺序:执行变量的初始化表达式 → 执行父类的(默认)构造函数 → 调用类型自己的构造函数

     1 public class A
     2 {
     3     public To t = new To("TO A");
     4 
     5     public A()
     6     {
     7         Console.WriteLine("A");
     8     }
     9 }
    10 public class B : A
    11 {
    12     public To t = new To("TO B");
    13 
    14     public B()
    15     {
    16         Console.WriteLine("B");
    17     }
    18 }
    19 public class C : B
    20 {
    21     public To t = new To("TO C");
    22 
    23     public C()
    24     {
    25         Console.WriteLine("C");
    26     }
    27 }
    28 public class To
    29 {
    30     public To(string msg)
    31     {
    32         Console.WriteLine(msg);
    33     }
    34 }
    35 public class RealizeObject
    36 {
    37     public void Realize()
    38     {
    39         C c = new C();
    40         //输出结果是:
    41         //TO C
    42         //TO B
    43         //TO A
    44         //A
    45         //B
    46         //C
    47     }
    48 }

    二、C#关键字:base

      继承的规则一说明子类无法使用父类的构造函数,所以我在文字类和图片类中创建了自己的构造函数。继承的规则二说明子类只能隐式地调用父类的默认构造函数,而无法调用父类的非默认构造函数,即无法复用父类的非默认构造函数,所以可以通过base关键字使子类的构造函数自定义调用父类的非默认构造函数。下面修改文字类和图片类使其复用父类的非默认构造函数:

     1 /// <summary>
     2 /// 文字
     3 /// </summary>
     4 public class Word : Information
     5 {
     6     public Word() { }
     7     public Word(string content, int size) : base(content, size);
     8 }
     9 /// <summary>
    10 /// 图片
    11 /// </summary>
    12 public class Picture : Information
    13 {
    14     /// <summary>
    15     /// 地址
    16     /// </summary>
    17     public string Path { get; set; }
    18 
    19     public Picture() { }
    20     public Picture(string content, int size, string path)
    21         : base(content, size)
    22     {
    23         this.Path = path;
    24     }
    25 
    26     /// <summary>
    27     /// 图片存储到文件中,并为Path赋值
    28     /// </summary>
    29     public void StoreToFile()
    30     {
    31 
    32     }
    33 }

    base关键字除了可以复用父类非默认构造函数之外,还可以复用父类的其他非私有成员(见C#多态)。

    总结:base关键字的使用方式同this关键字一样,区别在于this关键字指向本类,base关键字指向父类。

    三、C#关键字:sealed

      sealed关键字可以防止被继承或者被重写。

    1 /// <summary>
    2 /// 视频类(不能被其他类继承)
    3 /// </summary>
    4 public sealed class Video : Information { }

      注:sealed在防止被继承时多用于工具类。

      sealed防止被重写(见C#多态)。

    四、C#关键字:protected

      protected是专门用于继承中的访问修饰符,修饰在父类的成员上使其成员可被本类及其子类访问。

      注:protected多用于修饰父类的方法。

      访问修饰符直白对比:对全世界开放,使用public;只对本国开放,使用internal;只对家族开放,使用protected;只有自己知道,使用private。

    五、类型之间的关系:包含

      C#五大类型(类、接口、委托、枚举、结构)之间的相互嵌套即包含关系。既可以包含已定义类型也可以直接在被包含类型内定义类型。

      包含的作用同继承一样也是提高代码的复用性。

     1 /// <summary>
     2 /// 洗衣机类
     3 /// </summary>
     4 public class WashingMachine
     5 {
     6 
     7 }
     8 /// <summary>
     9 /// 房间类
    10 /// </summary>
    11 public class House
    12 {
    13     /// <summary>
    14     /// 房间类包含已定义的洗衣机类
    15     /// </summary>
    16     public WashingMachine washingMachine { get; set; }
    17 
    18     /// <summary>
    19     /// 直接在房间类中定义空调类
    20     /// </summary>
    21     public class AirConditioner
    22     {
    23 
    24     }
    25 
    26     /// <summary>
    27     /// 直接在房间类中定义性别枚举
    28     /// </summary>
    29     public enum Sex { man, woman }
    30 }
  • 相关阅读:
    时间戳 时间 相互转换
    CS Academy Remove Update
    一周水题集锦 2017 9.4
    计蒜客 16877 卡牌游戏
    计蒜客 16876 韩梅梅的抽象画
    九度OJ 题目1534:数组中第K小的数字
    CS Academy Switch the Lights
    CF AIM Tech Round 4 C. Sorting by Subsequences
    CF Round 430 C. Ilya And The Tree
    CS Academy Round 44 Check DFS
  • 原文地址:https://www.cnblogs.com/yaojieyuan/p/11558903.html
Copyright © 2011-2022 走看看