如何访问自动实现的属性的后备变量?


79

在过去,我们声明的属性如下:

public class MyClass
{
    private int _age;

    public int Age
    {
          get{ return _age;  }
          set{ _age = value; }
    }
}

现在我们可以做:

public class MyClass
{
    public int Age {get; set;} 
}

我的问题是,如何访问使用该符号自动创建的私有变量?

我宁愿访问私有变量,而不访问公共访问器“年龄”。是否存在访问私有变量的默认符号,或者只是不可能?


10
在访问私有访问者与公共访问者的情况下有什么区别?我认为,即使从声明类中的逻辑访问公共访问器也是最佳实践。如果您曾经向访问器添加了一些逻辑,则不需要更改所有代码。
Eric Sc​​hoonover,

@ spoon16您能否举个例子,向访问器添加逻辑并因此必须更改所有代码。我不太了解这部分。
Ogen 2014年

Answers:


92

新的自动属性的目的是减少仅具有简单属性的情况下所需编写的样板代码量,该简单属性在get或set中不需要任何特殊逻辑。

如果要访问这些属性使用的私有成员,通常是出于以下几个原因:

  • 您不仅需要简单的获取/设置-在这种情况下,您应该避免为此成员使用自动属性。
  • 您想避免经历get或set的性能下降,而直接使用成员-在这种情况下,如果确实有性能下降,我会感到惊讶。简单的get / set成员非常容易内联,在我的(公认的有限)测试中,我没有发现使用自动属性和直接访问该成员之间有什么区别。
  • 您只希望具有公共读取访问权限(即只是一个“ get”),并且该类直接写给成员-在这种情况下,您可以在自动属性中使用私有集。即

    public class MyClass
    {
        public int Age {get; private set;} 
    }

这通常涵盖了大多数希望直接进入自动属性所使用的后备字段的原因。


没错-他们确实减少了圆顶硬礼帽的代码,我也将做广告他们减少了您需要测试的内容。有人可能会争辩说,您需要测试手动获取/设置,而无需使用自动属性,因为您可以信任框架。
Daniel Auger

3
代码示例在这里是错误的。应该是公共类MyClass {public int Age {get; 私有集;}}我同意这个答案。您无法访问私有字段,并且如果需要,那么您首先不应该使用自动属性。
hwiechers

谢谢,谢谢-我进行了修改,但是在尝试修复格式时,我必须再次点击粘贴并删除了错误的代码块。h!
Wilka

常用于POCO对象
RobS

23

自动属性的使用意味着您不需要该属性的任何获取/设置逻辑,因此不需要私有后备变量。

如果您的班级中有任何复杂的逻辑,请不要使用自动属性。private int _age像往常一样去和普通的吸气剂/吸气剂。

IMO,自动属性更适合于快速实现一次性对象或临时数据封装,例如:

public class TempMessage {
    public int FromID { get; set; }
    public int ToID { get; set; }
    public string Message { get; set; }
}

您不需要太多逻辑的地方。


为什么在类中添加复杂的逻辑会影响您是否在该类中使用了自动属性?
埃里克·舒诺弗

更多的一致性问题...如果您具有复杂的逻辑,那么您将需要按照OO实践从私有支持变量访问它。.如果您使用自动属性,则...在访问这些属性时会出现不一致。因为有些会有下划线前缀,有些则没有。
chakrit

12

该语法通常称为“语法糖”,这意味着编译器采用该语法并将其转换为其他语法。在您的示例中,编译器将生成类似于以下内容的代码:

[CompilerGenerated]
private int <Age>k_BackingField;

public int Age
{
   [CompilerGenerated]
   get
   {
      return this.<Age>k_BackingField;
   }
   [CompilerGenerated]
   set
   {
      this.<Age>k_BackingField = value;
   }

即使知道所有这些,您也可能可以直接访问后备字段,但这种做法违反了使用自动属性的目的。我在这里说的可能是因为您依赖于实现细节,该细节在将来的C#编译器版本中可能随时发生变化。


10

幕后发生的事情是注入私有成员变量,其前缀为<> k__AutomaticallyGeneratedPropertyField#

C#3.0自动属性解释

尽管可以直接使用该私人成员,但它很hacky,没有必要。


7

您不应该,而且几乎不需要。如果您需要访问该属性,则只需使用公共属性(例如this.Age)。支持私有财产的私有领域没有什么特别的,优先使用私有财产是迷信。


1
我一直想知道自动属性的意义是什么。如果您的getter和setter中没有特殊的逻辑,为什么要完全使用它们呢?
马修·洛克

4
@MatthewLock的灵活性。借助直接现场访问,除非您同时更改所有客户端代码,否则您将被锁定在该设计中。但是对于属性,如果您决定将其从“伪字段”更改为计算属性,或者如果您决定添加断言并检查设置器或具有什么功能,则可以透明地进行。如果您正在编写无法控制所有客户端代码的库代码,这甚至会更加有用。

2

您不能,它是语言功能,而不是IDE功能。老实说,我宁愿选择IDE来为您添加私有变量。我同意类在内部不得不使用公共入口点来访问其自己的变量有点奇怪。因此,我本人并没有过多地使用此新功能。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.