关于c#:如何访问自动实现属性的后备变量?

关于c#:如何访问自动实现属性的后备变量?

How can I access the backing variable of an auto-implemented property?

在过去,我们声明的属性是这样的:

1
2
3
4
5
6
7
8
9
10
public class MyClass
{
    private int _age;

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

现在我们可以做:

1
2
3
4
public class MyClass
{
    public int Age {get; set;}
}

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

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


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

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

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

    1
    2
    3
    4
    public class MyClass
    {
        public int Age {get; private set;}
    }

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


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

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

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

1
2
3
4
5
public class TempMessage {
    public int FromID { get; set; }
    public int ToID { get; set; }
    public string Message { get; set; }
}

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


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

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
[CompilerGenerated]
private int <Age>k_BackingField;

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

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


Behind the scenes what happens is the injection of a private member variable, prefixed with <>k__AutomaticallyGeneratedPropertyField#

从C#3.0自动属性解释

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


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


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


推荐阅读