【C#语言规范版本5.0学习】1.5类和对象(三、其他函数成员)

 构造函数

C# 支持两种构造函数:实例构造函数静态构造函数

实例构造函数 (instance constructor) 是实现初始化类实例所需操作的成员。

静态构造函数 (static constructor) 是一种用于在第一次加载类本身时实现其初始化所需操作的成员。

构造函数的声明如同方法一样,不过它没有返回类型,并且它的名称与其所属的类的名称相同。如果构造函数声明包含 static 修饰符,则它声明了一个静态构造函数。否则,它声明的是一个实例构造函数。

实例构造函数可以被重载。例如,List 类声明了两个实例构造函数,一个无参数,另一个接受一个 int 参数。实例构造函数使用 new 运算符进行调用。下面的语句分别使用 List 类的每个构造函数分配两个 List 实例。

List list1 = new List();

List list2 = new List(10);

实例构造函数不同于其他成员,它是不能被继承的。一个类除了其中实际声明的实例构造函数外,没有其他的实例构造函数。如果没有为某个类提供任何实例构造函数,则将自动提供一个不带参数的空的实例构造函数。

 属  性

属性 (property) 是字段的自然扩展。

属性和字段都是命名的成员,都具有相关的类型,且用于访问字段和属性的语法也相同

然而,与字段不同,属性不表示存储位置。相反,属性有访问器 (accessor),这些访问器指定在它们的值被读取或写入时需执行的语句。

属性的声明与字段类似不同的是属性声明以位于定界符 { 和 } 之间的一个 get 访问器和/或一个 set 访问器结束,而不是以分号结束

同时具有 get 访问器和 set 访问器的属性是读写属性 (read-write property),只有 get 访问器的属性是只读属性 (read-only property),只有 set 访问器的属性是只写属性 (write-only property)。 get 访问器相当于一个具有属性类型返回值的无形参方法。除了作为赋值的目标,当在表达式中引用属性时,将调用该属性的 get 访问器以计算该属性的值。 set 访问器相当于具有一个名为 value 的参数并且没有返回类型的方法。

当某个属性作为赋值的目标被引用,或者作为 ++ 或 -- 的操作数被引用时,将调用 set 访问器,并传入提供新值的实参。 List 类声明了两个属性 Count 和 Capacity,它们分别是只读属性和读写属性。下面是这些属性的使用示例。

List<string> names = new List<string>();
names.Capacity = 100; // Invokes set accessor
int i = names.Count; // Invokes get accessor
int j = names.Capacity; // Invokes get accessor

与字段和方法相似,C# 同时支持实例属性和静态属性。静态属性使用 static 修饰符声明,而实例属性的声明不带该修饰符。 属性的访问器可以是虚的。

当属性声明包括 virtual、abstract 或 override 修饰符时,修饰符应用于该属性的访问器。

 索引器

索引器 (indexer) 是这样一个成员:它支持按照索引数组的方法来索引对象。索引器的声明与属性类似, 不同的是该成员的名称是 this,后跟一个位于定界符 [ 和 ] 之间的参数列表。

在索引器的访问器中可 以使用这些参数。与属性类似,索引器可以是读写、只读和只写的,并且索引器的访问器可以是虚的。 该 List 类声明了单个读写索引器,该索引器接受一个 int 参数。该索引器使得通过 int 值对 List 实例进行索引成为可能。例如

List<string> names = new List<string>();
names.Add("Liz");
names.Add("Martha");
names.Add("Beth");
for (int i = 0; i < names.Count; i++) {
string s = names[i];
names[i] = s.ToUpper();
}

索引器可以被重载,这意味着一个类可以声明多个索引器,只要其参数的数量和类型不同即可。

 事  件

事件 (event) 是一种使类或对象能够提供通知的成员。事件的声明与字段类似,不同的是事件的声明包含 event 关键字,并且类型必须是委托类型

在声明事件成员的类中,事件的行为就像委托类型的字段(前提是该事件不是抽象的并且未声明访问器)。

该字段存储对一个委托的引用,该委托表示已添加到该事件的事件处理程序。如果尚未添加事件处理程序,则该字段为 null。

List 类声明了一个名为 Changed 的事件成员,它指示已将一个新项添加到列表中。Changed 事件由 OnChanged 虚方法引发,后者先检查该事件是否为 null(表明没有处理程序)。

“引发一个事件” 与“调用一个由该事件表示的委托”这两个概念完全等效,因此没有用于引发事件的特殊语言构造。

客户端通过事件处理程序 (event handler) 来响应事件。事件处理程序使用 += 运算符附加,使用 -= 运算符移除。下面的示例向 List 类的 Changed 事件附加一个事件处理程序。

using System;
class Test
{
static int changeCount;
static void ListChanged(object sender, EventArgs e) {
changeCount++;
}
static void Main() {
List<string> names = new List<string>();
names.Changed += new EventHandler(ListChanged);
names.Add("Liz");
names.Add("Martha");
names.Add("Beth");
Console.WriteLine(changeCount); // Outputs "3"
}
}

对于要求控制事件的底层存储的高级情形,事件声明可以显式提供 add 和 remove 访问器,它们在某种程度上类似于属性的 set 访问器。

 运算符

运算符 (operator) 是一种类成员,它定义了可应用于类实例的特定表达式运算符的含义。可以定义三类运算符:一元运算符、二元运算符和转换运算符。所有运算符都必须声明为 public 和 static。 List 类声明了两个运算符 operator == 和 operator !=,从而为将那些运算符应用于 List 实例的表达式赋予了新的含义。具体而言,上述运算符将两个 List 实例的相等关系定义为逐一比较其中所包含的对象(使用所包含对象的 Equals 方法)。下面的示例使用 == 运算符比较两个 List 实例。

using System;
class Test
{
static void Main() {
List<int> a = new List<int>();
a.Add(1);
a.Add(2);
List<int> b = new List<int>();
b.Add(1);
b.Add(2);
Console.WriteLine(a == b); // Outputs "True"
b.Add(3);
Console.WriteLine(a == b); // Outputs "False"
}
}

第一个 Console.WriteLine 输出 True,原因是两个列表包含的对象数目、对象顺序和对象值都相同(根据自定义的方法)。 如果 List 未定义 operator ==,则第一个 Console.WriteLine 将输出 False,原因是 a 和 b 引用的是不同的 List 实例。

C#中Equals和= =(等于号)的比较,链接:

https://www.cnblogs.com/changbaishan/p/10579021.html

 析构函数

析构函数 (destructor) 是一种用于实现销毁类实例所需操作的成员

析构函数不能带参数,不能具有可访问性修饰符,也不能被显式调用

垃圾回收期间会自动调用所涉及实例的析构函数。

垃圾回收器在决定何时回收对象和运行析构函数方面允许有广泛的自由度。具体而言,析构函数调用的时机并不是确定的,析构函数可以在任何线程上执行。

由于这些以及其他原因,仅当没有其他可行的解决方案时,才应在类中实现析构函数。 using 语句提供了更好的对象析构方法。

posted @ 2021-01-26 16:33  TechSingularity  阅读(154)  评论(0编辑  收藏  举报