📜  C#|特性

📅  最后修改于: 2021-05-29 22:35:08             🧑  作者: Mango

在继续使用属性之前,让我们看一下为什么C#中引入了属性的概念?的原因有两个:

  • 如果一个类的成员是私有的,那么C#中的另一个类将如何读取,写入或计算该字段的值。
  • 如果班级成员是公开的,则另一个班级可能会滥用该成员。

例子:

// C# program to illustrate the problems
// with public and private members
using System;
  
// public class
public class C1
{
      
    // public data members
    public int rn;
    public string name;
      
    // private field
    // private int marks = 35;
  
}
  
// another public class
public class C2
{
      
// Main Method
public static void Main(string[] args)
{
      
    // Creating object of C1 class
    C1 obj = new C1();
      
    // setting values to public
    // data members of class C1
    obj.rn = 10000;
    obj.name = null;
      
    // setting values to private
    // data members of class C1
    // obj.mark = 0;
      
    // display result
    Console.WriteLine("Name:  {0} \nRoll No: {1}", obj.name, obj.rn);
      
}
}

输出:

Name:   
Roll No: 10000

说明:在上面,您可以看到类C2可以访问类C1的公共成员,并且使用对象C1的“ obj”可以向成员提供值,例如Name的值为null,但是我们不希望这样做为空。 C2无法将值提供给成员“标记”,因为它在C1中是私有的。要测试私有成员访问权限,请删除注释并尝试运行,您会看到编译器将给出错误。不具有属性的编程语言使用getter和setter方法来提供这种访问机制。

使用属性

属性是类成员的特殊类型,它提供了一种灵活的机制来读取,写入或计算私有字段的值。可以将属性当作公共数据成员使用,但实际上它们是称为accessors的特殊方法。这使数据易于访问,并有助于提高方法的灵活性和安全性。信息的封装和隐藏也可以使用属性来实现。它使用预定义的方法(即“ get”和“ set”方法)来帮助访问和修改属性。

存取器: “设置”和“获取”的块称为“存取器”。限制财产的可及性非常重要。访问器有两种类型,即获取访问器设置访问器。基于“获取”和设置访问器的属性有不同类型:

  • 读取和写入属性:当属性同时包含get和set方法时。
  • 只读属性:当属性仅包含get方法时。
  • 只写属性:当属性仅包含set方法时。
  • 自动实现的属性:当属性访问器中没有其他逻辑时,它将在C#3.0中引入。

定义属性的语法:

  
{
        get { // body }
        set { // body }
}

其中,可以是公共的,私有的,受保护的或内部的。 可以是任何有效的C#类型。 可以是用户定义的。属性可以是不同的访问修饰符,例如public,private,protected,internal。访问修饰符定义类的用户如何访问属性。相同属性的get和set访问器可能具有不同的访问修饰符。可以使用static关键字将属性声明为静态属性,也可以使用virtual关键字将属性标记为虚拟属性

  • 获取访问器:指定字段的值可以公开访问。它返回一个值,并指定只读属性

    例子:

    class Geeks {
    // Declare roll_no field
    private int roll_no;
    
    // Declare roll_no property
    public int Roll_no 
    { 
    
       get 
         {
          return roll_no;
         }
    
    }
    }
    
  • 设置访问器:它将为属性中的私有字段指定值的分配。它返回一个值,并指定只写属性

    例子:

    class Geeks {
    
    // Declare roll_no field
    private int roll_no;
    
    // Declare roll_no property
    public int Roll_no
     { 
    
       get 
         {
             return roll_no;
          }
    
       set 
         {
             roll_no = value;
          }
    }
    }
    

访问器可访问性

  • 我们不能在接口或显式接口成员实现上使用存取修饰符。
  • 只有在属性同时具有set和get访问器的情况下,我们才可以使用accessor修饰符。
  • 如果该属性是覆盖修改器,则访问器修改器必须与覆盖的访问器的访问器匹配。
  • 访问者上的可访问性级别必须比属性上的可访问性级别更具限制性。

以下是演示不同类型属性的程序:

程序1:使用“ get”访问器演示只读属性。

// C# program to illustrate the
// read-only property
using System;
  
public class Student {
  
    // Declare counter field as cnt
    private static int cnt; 
   
    // to define constructor
    public Student()
    {
  
        // increment the counter 
        // using constructor
        cnt++; 
    }
   
    // Declare counter property
    public static int Counter 
    {
  
        // read-only property
        get
        {
            return cnt;
        }
    }
}
  
class StudentTest {
  
    // Main Method
    public static void Main(string[] args)
    {
  
        // create three instances of
        // Student class it call constructor
        // three times which increase the counter
        Student s1 = new Student();
        Student s2 = new Student();
        Student s3 = new Student();
   
        // s1.Counter = 10;
        // Compile Time Error: Can't set value of
        // Counter because it is read only.
   
        Console.WriteLine("Total No of Student: " + Student.Counter);
   
        // Program Give Warning
        // The variable `s1' is assigned but its value is never used
    }
}

输出:

Total No of Student: 3

程序2:使用“ get”和“ set”访问器演示读写属性。

// C# program to illustrate the 
// read and wirte property
using System;
  
public class Student {
  
    // Declare name field
    private string name = "GeeksforGeeks"; 
   
    // Declare name property
    public string Name 
    {
  
       get
        {
            return name;
        }
  
        set
        {
            name = value;
        }
    }
}
  
class TestStudent {
  
    // Main Method
    public static void Main(string[] args)
    {
        Student s = new Student();
   
        // calls set accessor of the property Name,
        // and pass "GFG" as value of the
        // standard field 'value'.
        s.Name = "GFG";
   
        // displays GFG, Calls the get accessor
        // of the property Name.
        Console.WriteLine("Name: " + s.Name);
    }
}

输出:

Name: GFG