接口:接通过使⽤接⼝,可以在选件类中,例如,包括从多个源的⾏为。 由于C#语⾔不⽀持多重继承,所以该功
能很重要。 此外,您必须使⽤接⼝,如果要模拟结构的继承,因为它们不能从另⼀个结构或选件类实际继承。
通过使⽤interface关键字,定义⼀个接⼝。
实现接⼝的任何类或结构必须实现其所有成员的⽅法。
接⼝不能直接实例化, 但是可以通过指向⼦类间接实例化。
接⼝可以包含⽅法和属性的声明,但不能包含字段。
接⼝中所有⽅法、属性默认为public,不能在后⾯再添加修饰符。
类或结构可以实现多个接⼝。 类可以继承基类并实现⼀个或多个接⼝。
接⼝与抽象类⾮常相似,它定义了⼀些未实现的属性和⽅法。所有继承它的类都继承这些成员,在这个⾓度上,
可以把接⼝理解为⼀个类的模板。 接⼝最终的⺫的是起到统⼀的作⽤。
抽象类除拥有抽象成员之外,还可以拥有⾮抽象成员;⽽接⼝所有的成员都是抽象的。抽象成员可以是私有的,
⽽接⼝的成员默认是公有的。接⼝中不能含有构造函数、析构函数、静态成员和常量。
C#只⽀持单继承,即⼦类只能继承⼀个⽗类,⽽⼀个⼦类却能够实现多个接⼝。
interface IUSB { string[] Datas{ get; set; } void Read(string[] datas); } interface IBlueTooth { void Write(string[] datas); } class Video { } class Mp3 : Video, IUSB, IBlueTooth { protected string[] datas; public string[] Datas { get { return datas; } set { datas = value; } } //实现IUSB的方法 public void Read(string[] datas) { Console.WriteLine("从电脑中读取数据"); foreach (string item in datas) { Console.WriteLine("读取数据是:{0}", item); } } //实现Bluetooth的方法 public void Write(string[] datas) { Console.WriteLine("往电脑中写数据"); foreach (string item in datas) { Console.WriteLine(item); } } }
泛型:我们在编写程序时,经常遇到两个模块的功能⾮常相似,只是⼀个是处理int
数据,另⼀个是处string数据,或者其他⾃定义的数据类型,但我们没有办
法,只能分别写多个⽅法处理每个数据类型,因为⽅法的参数类型不同。
你可能会想到⽤object,来解决这个问题。但是,缺陷的:
1.会出现装箱、折箱操作,这将在托管堆上分配和回收⼤量
的变量,若数据量⼤,则性能损失⾮常严重。
2.在处理引⽤类型时,虽然没有装箱和折箱操作,但将⽤到
数据类型的强制转换操作,增加处理器的负担。
C#中的泛型能够将类型作为参数来传递,即在创建类型时⽤⼀个特定的符号如“T”来作为
⼀个占位符,代替实际的类型,等待在实例化时⽤⼀个实际的类型来代替。
泛型有点:⼀、使⽤泛型类型可以最⼤限度地重⽤代码、保护类型的安全以及提⾼性能。
⼆、降低了强制转换或装箱操作的成本或⻛险。
三、 可以对泛型类进⾏约束以访问特定数据类型的⽅法。
泛型参数:在泛型类型或⽅法定义中,类型参数是客户端在实例化泛型类型的变量时指定
的特定类型的占位符。
1.类型参数并不是只有⼀个,可以有多个。
2.类型参数可以是编译器识别的任何类型。
3.类型参数的名字不能随便起,不能重名。
在定义泛型类时,可以对客户端代码能够在实例化类时⽤于类型参数
的类型种类施加限制。 如果客户端代码尝试使⽤某个约束所不允许的
类型来实例化类,则会产⽣编译时错误。 这些限制称为约束。 约束是
使⽤ where 上下⽂关键字指定的。
泛型类:泛型类封装不是特定于具体数据类型的操作。泛型类最常⽤于集合。
像从集合中添加和移除项这样的操作都以⼤体上相同的⽅式执⾏,与
所存储数据的类型⽆关。
创建泛型类的过程为:从⼀个现有的具体类开始,逐⼀将每个类型更
改为类型参数,直⾄达到通⽤化和可⽤性的最佳平衡。
泛型方法:创建泛型⽅法的过程和泛型类相似。泛型⽅法是使⽤类型参数声明的⽅法
class MyList<T> { T[] arr = new T[2]; public MyList(T a, T b) { T[] temp = {a,b}; arr = temp; } private int count; public int Count { get { return count; } set { count = value; } } public void Clear() { arr = null; } public void Show() { foreach (T x in arr) { Console.Write(x+" "); } Console.WriteLine(); } public void Add(T a) { T[] temp = new T[arr.Length + 1]; for (int i = 0; i < arr.Length ; i++) { temp[i] = arr[i]; } temp[arr.Length] = a; arr = temp; } public void Insert(T value, int index){ T[] temp = new T[arr.Length + 1]; for (int i = 0; i < index; i++) { temp[i] = arr[i]; } temp[index] = value; for (int i = index+1; i < arr.Length+1; i++) { temp[i] = arr[i-1]; } arr = temp; } public void Reverse() { for (int i = 0; i < arr.Length/2; i++) { T temp = arr[i]; arr[i] = arr[arr.Length - 1 - i]; arr[arr.Length - 1 - i] = temp; } } }
MyList<int> test = new MyList<int>(3, 5); test.Show(); test.Add(6); test.Show(); test.Insert(1, 2); test.Show(); test.Reverse(); test.Show();