类的字段和属性

本文介绍了C#中字段的概念,包括静态字段、实例字段、常量和只读字段,并详细解释了属性的作用及其实现方式,展示了如何通过属性增强类的封装性和安全性。
类的字段和属性
 一般把类或结构中定义的变量和常量叫字段。属性不是字段,本质上是定义修改字段的方法,由于属性和字段的紧密关系,把它们放到一起叙述。
静态字段、实例字段、常量和只读字段
 用修饰符static声明的字段为静态字段。不管包含该静态字段的类生成多少个对象或根本无对象,该字段都只有一个实例,静态字段不能被撤销。必须采用如下方法引用静态字段:类名.静态字段名。如果类中定义的字段不使用修饰符static,该字段为实例字段,每创建该类的一个对象,在对象内创建一个该字段实例,创建它的对象被撤销,该字段对象也被撤销,实例字段采用如下方法引用:实例名.实例字段名。用const修饰符声明的字段为常量,常量只能在声明中初始化,以后不能再修改。用readonly修饰符声明的字段为只读字段,只读字段是特殊的实例字段,它只能在字段声明中或构造函数中重新赋值,在其它任何地方都不能改变只读字段的值。例子:
public class Test
{ public const int intMax=int.MaxValue;//常量,必须赋初值
 public int x=0;//实例字段
 public readonly int y=0;//只读字段
 public static int cnt=0;//静态字段
 public Test(int x1,int y1)//构造函数
 { //intMax=0;//错误,不能修改常量
  x=x1;//在构造函数允许修改实例字段
  y=y1;//在构造函数允许修改只读字段
  cnt++;//每创建一个对象都调用构造函数,用此语句可以记录对象的个数
 }
 public void Modify(int x1,int y1)
 { //intMax=0;//错误,不能修改常量
  x=x1;
  cnt=y1;
  //y=10;//不允许修改只读字段
 }
}
class Class1
{ static void Main(string[] args)
 { Test T1=new Test(100,200);
  T1.x=40;//引用实例字段采用方法:实例名.实例字段名
   Test.cnt=0;//引用静态字段采用方法:类名.静态字段名
  int z=T1.y;//引用只读字段
   z=Test.intMax;//引用常量
 }
}
属性
 C#语言支持组件编程,组件也是类,组件用属性、方法、事件描述。属性不是字段,但必然和类中的某个或某些字段相联系,属性定义了得到和修改相联系的字段的方法。C#中的属性更充分地体现了对象的封装性:不直接操作类的数据内容,而是通过访问器进行访问,借助于get和set方法对属性的值进行读写。访问属性值的语法形式和访问一个变量基本一样,使访问属性就象访问变量一样方便,符合习惯。
 在类的基本概念一节中,定义一个描述个人情况的类Person,其中字段name和age是私有字段,记录姓名和年龄,外部通过公有方法SetName和SetAge修改这两个私有字段。现在用属性来描述姓名和年龄。例子如下:
using System;
public class Person
{ private string P_name="张三"; //P_name是私有字段
 private int P_age=12; //P_age是私有字段
 public void Display() //类的方法声明,显示姓名和年龄
 { Console.WriteLine("姓名:{0},年龄:{1}",P_name,P_age);
 }
 public string Name //定义属性Name
 { get
  { return  P_name;}
  set
  { P_name=value;}
 }
 public int Age //定义属性Age
 { get
  { return  P_age;}
  set
  { P_age=value;}
 }
}
public class Test
{ public static void Main()
 { Person OnePerson= new Person();
  OnePerson.Name="田七";//value="田七",通过set方法修改变量P_Name
  string s=OnePerson.Name;//通过get方法得到变量P_Name值
  OnePerson.Age=20;//通过定义属性,既保证了姓名和年龄按指定方法修改
  int x=OnePerson.Age;//语法形式和修改、得到一个变量基本一致,符合习惯
 OnePerson.Display();
 }
}
 在属性的访问声明中,只有set访问器表明属性的值只能进行设置而不能读出,只有get访问器表明属性的值是只读的不能改写,同时具有set访问器和get访问器表明属性的值的读写都是允许的。
虽然属性和字段的使用方法类似,但由于属性本质上是方法,因此不能把属性当做变量,一些使用变量的地方并不能使用属性,例如不能把属性作为函数的引用型参数或输出参数。
 
### 字段属性的区别 #### 定义用途 字段或结构体中用于存储数据的成员变量,通常被声明为 `private` 或 `protected` 以限制外部直接访问。字段主要用于内部状态的维护,并不提供对数据访问的额外控制[^3]。 属性则是或结构体的成员,提供了一种控制对字段访问的方式。通过 `get` `set` 访问器,属性允许在读取写入数据时执行额外逻辑,例如数据验证、触发事件等。这使得属性不仅能够封装字段,还能增强数据的安全性灵活性[^2]。 #### 封装性 字段通常用于内部的数据存储,而属性提供了一种机制来控制这些字段的访问,从而实现更好的封装。即使是最简单的数据存取操作,推荐使用自动属性(auto-implemented properties)而非公共字段,因为这样可以提高代码的可维护性安全性[^4]。 ```csharp public class Person { // 字段 private string _name; // 属性 public string Name { get { return _name; } set { _name = value; } } } ``` #### 控制逻辑 通过属性的 `get` `set` 访问器,可以在读写数据时添加特定的逻辑,比如验证输入数据或修改其他字段的值。相比之下,字段并不具备这种控制机制,任何对字段的操作都是直接且无条件的[^5]。 ```csharp public class Person { private string name; private int age; public string Name { get { return name; } set { if (string.IsNullOrEmpty(value)) throw new ArgumentException("Name cannot be null or empty."); name = value; } } public int Age { get { return age; } set { if (value < 0) throw new ArgumentException("Age cannot be negative."); age = value; } } } ``` #### 数据绑定支持 在某些情况下,如数据绑定方面,通常需要使用属性而不是字段,因为许多框架库是通过属性进行数据绑定的。这意味着如果希望某个支持数据绑定,则必须将相关成员定义为属性形式。 #### 设计原则 按照 C# 的设计原则,公共数据成员应该被声明为属性而不是公共字段。即使是简单的数据存取操作,也建议使用自动属性来提供更好的封装效果。这样做有助于保持良好的编程实践,并确保未来的扩展性兼容性[^4]。 ```csharp // 自动实现的属性示例 public class Person { public string Name { get; set; } public int Age { get; set; } } ``` #### 使用方式 当创建一个对象并对其进行初始化时,可以通过属性来进行赋值获取值的操作。由于属性提供了额外的安全检查功能,因此它们比直接操作字段更加安全可靠[^1]。 ```csharp internal class Program { static void Main(string[] args) { People people = new People(); // 对私有字段赋值,就是调用属性Age的set方法 people.Age = 20; // 对私有字段取值,就是调用属性Age的get方法 Console.WriteLine(people.Age); } } internal class People { private int _age; public int Age { get { return _age; } set { _age = value; } } } ```
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值