【问题标题】:What is the difference between prop and a full property?prop 和 full 属性有什么区别?
【发布时间】:2011-09-15 16:32:00
【问题描述】:

下面两段代码有什么区别吗?还是顶部只是底部的缩写形式?

public string Name { get; set; }

private string _Name;
public string Name
{
    get { return _Name; }
    set { _Name = value; }
}

【问题讨论】:

标签: c# properties


【解决方案1】:

唯一的区别(除了您必须在类构造函数中使用“默认名称”进行初始化之外)是_Name 将在类本身中可见。存在该类将在内部引用 _Name 而不是 Name 的风险,一切都会正常工作,并且稍后您将向 Name 添加一些不会被调用的逻辑,因为您正在使用班级内_Name

例子:

private string _Name = "Default Name";
public string Name
{
   get { return _Name.Left(42); }  // Changed the getter
   set { _Name = value; }
}

void MyOtherMethod()
{
   string foo = _Name; // Referencing the private field accidentally instead of the public property.
   // Do something with foo
}

【讨论】:

    【解决方案2】:

    这两种属性方法的基本行为和目的几乎相同。但主要区别在于实施。区别

    public string Name{get;set;}
    

     private string _Name;
            public string Name
            {
                get { return _Name; }
                set { _Name=value;  }
            }
    

    如果您使用短属性语法(在框架 3.0 或更高版本中引入),则属性字符串永远不会初始化,即如果您直接在任何地方使用“名称”属性而不为其设置值,它将返回 NULL 值。但是,如果您使用第二种语法来初始化属性值,它将返回一个 EMPTY 字符串,因为当您初始化一个字符串时,它会使用 EMPTY 值而不是 NULL 进行初始化。因此,如果您在未使用 FULL 属性方法初始化的情况下返回属性值,它将始终返回 EMPTY 字符串而不是 NULL 值。

    【讨论】:

    • 我已经测试过了,两种情况都返回一个空值的名称:dotnetfiddle.net/jqFXdl(也在 .NET Framework 2.0、3.0 和 3.5 中测试过)
    • 提供的答案很旧,不适用于较新版本的 C#。自动属性初始化器在过去几年中发生了很大变化。
    【解决方案3】:

    我认为编译后的代码没有任何区别。你可能想要完整的方式的原因是如果你想添加一个默认值(可以在构造函数中以简写形式完成),或者向 getter 或 setter 添加额外的代码

    编辑:实际上,您的代码应该是错误的

    private string _Name;
    public string Name
    {
       get { return _Name; }
       set { _Name = value; }//change here
    }
    

    不是……

    value = _Name;
    

    【讨论】:

    • 意识到这个问题已经过时了,这在 C# 6.0 中发生了变化,因为可以使用默认值初始化自动属性。请参阅stackoverflow.com/questions/40730/… 了解更多信息。
    【解决方案4】:

    其中一个区别是您可以在执行此操作时在私有字符串上设置默认值

    private string _Name = "Default Name";
    public string Name
    {
       get { return _Name; }
       set { value = _Name; }
    }
    

    编译后显示的两个示例是相同的。

    【讨论】:

      【解决方案5】:

      它只是一个简短的形式,基础变量仍然作为支持支持字段(存储数据的位置)生成,但自动生成 - 如果您实际上只是获取和设置并且不需要任何特定的任一访问器中的实现细节。

      【讨论】:

        【解决方案6】:

        对于第二种形式的这种特殊实现,两者是等价的。因为如果你只写第一种形式,编译器将生成几乎相同的代码。

        也就是说,编译器要给它加代码:

        public string Name{get;set;}
        

        让它看起来像这样:

        private string generatedCode_Name;
        public string Name
        {
              get { return generatedCode_Name; }
              set { generatedCode_Name = value; }
        }
        

        顺便说一句,这是不正确的

        set { value = _Name; } //I believe its a typo!
        

        我想你的意思是:

        set {  _Name = value; }
        

        【讨论】:

          【解决方案7】:

          对于所写的示例,它们是完全等价的。

          Auto-implemented properties 是为了解决这类情况而引入的语法糖,其中使用属性只是为了避免拥有公共字段,而在 getter/setter 中没有额外的逻辑。但是,自动实现的属性为您提供属性的所有好处,包括元数据。这是一个相当old but still relevant link,它解释了更多关于它们的信息。

          在幕后,编译器会生成一个与您自己的非常相似的支持字段。

          【讨论】:

            猜你喜欢
            • 2019-02-19
            • 2014-12-08
            • 2011-11-14
            • 2012-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2010-09-20
            相关资源
            最近更新 更多