封装和抽象
C#是一种面向对象的编程语言,其中抽象和封装是面向对象编程中的两个核心概念。
-
抽象(Abstraction):
抽象是将具有相似特征和行为的对象抽象出来形成类的过程。在 C# 中,我们可以使用抽象类和接口来实现抽象。 -
封装(Encapsulation):
封装是将数据和行为包装在一起形成类的过程,将数据隐藏在类的内部,只能通过类的公共方法来访问和修改。C# 中,我们可以使用访问修饰符来实现封装,如private
、protected
、internal
和public
等。- 私有成员只能在类的内部访问,受保护的成员可以在派生类中访问,内部成员可以在同一个程序集中访问,公共成员可以被所有代码访问。
- 通过封装,可以避免数据被误用或修改,增强了程序的安全性和可维护性。
访问修饰符——变量、方法的私有化与公有化
在C#中,可以使用访问修饰符来指定变量和方法的访问级别,从而决定它们能否被其他类或对象访问。常用的访问修饰符有以下四种:
public
:公共访问修饰符,表示该变量或方法可以被外部所有类和对象访问。
- 构造函数通常就需要使用public访问修饰符(还有的使用static静态修饰符),因为当你创建一个类的对象时,你需要调用该类的构造函数来初始化对象的成员变量和属性等信息。如果构造函数的访问修饰符不是public,那么在类的外部就无法调用该构造函数,也就无法创建该类的对象。
- unity中的编辑器也会识别public变量并显示在Inspector窗口中,从而在对应脚本选项卡内就能对该变量进行修改设置,修改的值会被保存到c#脚本文件当中。
private
:私有访问修饰符,表示该变量或方法只能被定义它们的类内部的其他成员访问。
- 即使是该类的实例也不能访问它的私有成员,因为实例对象位于类的外部。
protected
:受保护访问修饰符,表示该变量或方法只能被定义它们的类内部及其子类中的其他成员访问。
- 这样有助于实现继承,我们将在继承的章节详细讨论这个。
- Protected Internal 访问修饰符允许在本类、派生类或者包含该类的程序集中访问,这也被用于实现继承。
internal
:内部访问修饰符,表示该变量或方法只能被当前程序中的其他类和对象访问。
- 在当前这个文件中效用等同于 public,但当其他文件引入当前文件的类时,将无法访问 internal 定义的类、方法和对象。
需要注意访问修饰符的使用存在一些限制,详见官方文档。
用一个比较形象的描述来理解这几个访问修饰符的区别:
下面的代码演示了如何使用访问修饰符来控制变量和方法的访问级别:
public class MyClass
{
public int publicVar; // 公共变量
private int privateVar; // 私有变量
protected int protectedVar; // 受保护变量
internal int internalVar; // 内部变量
public void PublicMethod() // 公共方法
{
// 方法实现
}
private void PrivateMethod() // 私有方法
{
// 方法实现
}
protected void ProtectedMethod() // 受保护方法
{
// 方法实现
}
internal void InternalMethod() // 内部方法
{
// 方法实现
}
}
在上面的代码中,MyClass类包含了四个不同访问级别的变量和方法。可以看到,公共变量和方法使用public访问修饰符声明,私有变量和方法使用private访问修饰符声明,受保护变量和方法使用protected访问修饰符声明,而内部变量和方法使用internal访问修饰符声明。这样,其他类或对象就可以根据访问修饰符的不同来访问或者不能访问这些成员。
静态修饰符——变量、方法的归属权变更
在C#中,静态修饰符可以用来指定类成员是静态的,也就是说它们属于类而不属于对象。当一个类成员被声明为静态时,可以直接通过类名来访问它,而不需要先创建类的实例。
静态修饰符可以用于以下几种类成员:
-
静态字段:静态字段是类的字段,而不是实例的字段,它们只有一个副本,被类的所有实例共享。
-
静态方法:静态方法是类的方法,而不是实例的方法,它们不需要通过类的实例来调用,可以直接通过类名调用。
-
静态构造函数:静态构造函数是在类的第一个实例被创建之前自动调用的,用于初始化静态数据。
例如,下面的代码演示了如何使用静态修饰符来声明静态字段和静态方法:
public class MyClass
{
public int instanceVar; // 实例变量
public static int staticVar; // 静态变量
public void InstanceMethod() // 实例方法
{
// 方法实现
}
public static void StaticMethod() // 静态方法
{
// 方法实现
}
}
在上面的代码中,MyClass类包含了一个实例变量instanceVar和一个静态变量staticVar。实例方法InstanceMethod只能通过类的实例来调用,而静态方法StaticMethod可以通过类名来调用。
注意:静态方法只能访问静态成员,不能访问实例成员。同时,静态方法也不能访问实例的this指针。
静态构造函数和一般构造函数的区别
C#中的静态构造函数和一般构造函数的主要区别如下:
-
调用时机不同:静态构造函数在类被首次实例化时自动调用,而一般构造函数在每次创建实例对象时调用。
-
调用方式不同:静态构造函数没有访问修饰符,也不能被显式调用,而一般构造函数可以通过类的实例来调用。
-
作用域不同:静态构造函数只能访问静态成员,而一般构造函数可以访问所有成员。
-
参数不同:静态构造函数没有参数(因为无法显示调用,且只能访问静态成员),而一般构造函数可以有任意个参数。
-
返回值不同:静态构造函数没有返回值,而一般构造函数没有返回值类型声明(连void也不需要添加),因为它们总是返回创建的实例对象本身。
以下是一个示例代码来对比静态构造函数和一般构造函数的区别:
public class MyClass
{
static int staticField;
int instanceField;
// 静态构造函数
static MyClass()
{
Console.WriteLine("静态构造函数被调用");
staticField = 10;
}
// 一般构造函数
public MyClass(int value)
{
Console.WriteLine("一般构造函数被调用");
instanceField = value;
}
}
class Program
{
static void Main(string[] args)
{
// 调用静态构造函数
MyClass myClass1 = new MyClass(1);
// 创建对象并调用一般构造函数
MyClass myClass2 = new MyClass(2);
}
}
输出结果:
静态构造函数被调用
一般构造函数被调用
一般构造函数被调用
从输出结果可以看出,静态构造函数在类被首次实例化时自动调用;而一般构造函数在每次创建对象时调用。此外,静态构造函数只会被调用一次,而一般构造函数会被每次创建对象时调用。