C# 为什么类成员是私有的而属性是公共的?
在类中,我们将类成员声明为private,但将属性定义为public 例如:C# 为什么类成员是私有的而属性是公共的?,c#,C#,在类中,我们将类成员声明为private,但将属性定义为public 例如: public class student { private int StudentId; private string StudentName; private string Address; } 然后我们用方法赋值 但是如果我们使用get set的属性定义public-like public class student { public int StudentId {get;se
public class student
{
private int StudentId;
private string StudentName;
private string Address;
}
然后我们用方法赋值
但是如果我们使用get set的属性定义public-like
public class student
{
public int StudentId {get;set;};
public string StudentName{get;set;};
public string Address{get;set;};
}
这背后的原因是什么?类需要控制其公共成员的行为:即控制他们的行为 想象一下,例如,如果
私有字符串StudentName代码>是公开的,因此被外部代码使用(课外学生)。然后,您决定要添加验证以限制StudentName
的长度-如何才能做到这一点?您必须在您的代码(可能还有使用该类的其他人的代码)中找到设置StudentName
值的所有实例,并在其中添加验证
如果您使用的是公共字符串Student{get;set;}
,则不会这样做-您可以通过验证轻松将其更改为显式属性:
private string _student;
public string Student
{
get { return _student; }
set { if(value.Length <= 20) _student = value;
}
private string\u学生;
公共弦乐学生
{
获取{return\u student;}
set{if(value.Length您是对的-属性通常用作公共属性。
但是:您也可以定义如下属性:
这将使其他类获得您的属性的值,但它们无法更改它
想象一下,如果你要开发一个像程序集一样的项目,其中包含许多复杂的控件。如果你想让用户能够阅读,控件中的值是多少,因为它是经过计算的,你给它一个公共的getter,但给它一个私有的setter,因为你不希望有人操纵内部发生的事情。这不完全是真的规则是:
尽可能严格地定义所有成员
因此,如果它可以是私有的
,那么它就是私有的
。否则如果它必须是内部的
或受保护的
才能工作,那么它就分别是内部的
或受保护的
。否则,如果它必须是受保护的内部的
才能工作,那么它就是受保护的内部的
t的public
,因为它必须是public
才能工作(程序集之外的某个不从它继承的东西将不得不访问它)
现在,所有这些都表明,通常情况下,我们会有大部分的私有
字段和大部分的公共
属性
让我们考虑一下,如果我们有一个<代码>公共<代码>字段。它是有效的,可以工作,甚至在非常有限的情况下也是有用的。但是它也更脆弱。如果它<代码>公共< /代码>,让任何其他代码将它设置为任何值,无论多么愚蠢。没关系,因为当我们制定一个字段<代码>公共< /代码>时,我们在说。“没有愚蠢的价值观”*
但是,如果我们突然意识到存在一些愚蠢的值,或者每次字段被更改时我们都需要做一些事情,或者我们需要使用一些仅属性的数据绑定。在这里,我们必须将字段转换为属性,这是一个突破性的更改;任何使用该类的代码都必须重新编译,这不是一个大问题如果我们是唯一使用该类的人,但如果该类位于其他人正在使用的库中,则进行交易
但是,如果它是一个属性,那么我们只需将一个自动属性{get;set;}
转换为一个具有自定义实现的属性{get{/*do stuff并返回值*/}set{/*do stuff*/}
。从类外部看,它似乎没有发生任何变化,我们也没有破坏任何东西
因此,99.99%的情况下,如果你打算将一个字段公开
,你最好在那里使用一个属性,以防万一
另一方面,如果我们有一个没有逻辑的private
属性,那么getter和setter方法不会给我们带来任何好处。不会有任何成本,但它们是毫无意义的。所以我们只使用一个字段。如果我们将来不得不使用私有属性,那也没关系,因为唯一需要重新编译的代码是d就是这个问题中的类,我们正在重新编译它
因此,我们以几乎所有字段都是private
而几乎所有没有任何自定义逻辑的属性都是受保护的
或public
的情况结束
*或者它是一个private
或internal
类,我们从外部承诺不会将其设置为愚蠢的东西,但最好是强制执行承诺,而不是在可能的情况下做出承诺。不直接设置字段,而是通过属性遵循面向对象的封装原则。这包括类是bos类应该始终控制对其数据的访问(无论是读还是写)。有时这意味着它们需要执行额外的步骤来确保数据一致性。但即使它们不这样做,调用方也应该隐藏不这样做的事实,因为这与它们无关(关注点分离)。因此,一条简单的规则是:对象数据没有捷径。如果你想获取其中的一部分,你必须要求类将其提供给你。在C#中,这就是属性的用途。使用属性并将其公开背后有多种原因
将类字段标记为public&公开是一种风险,正如您将看到的那样
无法控制分配和返回的内容
要在值更改时进入调试器吗?只需在setter中添加一个断点
要记录所有访问吗?只需将日志添加到getter。
属性用于数据绑定;字段不用于数据绑定
在私有成员上添加验证(如值不能设置为负值)
如果为null、空或零,则返回一些默认值
属性可以声明为读/写、只读或只读
其他好处,反射和数据绑定
我在那里
public int StudentId {get; private set;}
public interface IStudent
{
int StudentId { get; set; }
string StudentName { get; set; }
string Address { get; set; }
}
public class Student : IStudent
{
public int StudentId { get; set; }
public string StudentName { get; set; }
public string Address { get; set; }
}