2013-02-19 25 views
2

来自C#4.0第7.5.5节。如何在构造后修改值类型的只读字段

如果M是一个值类型中声明的实例函数成员:

  • [...]
  • 如果E没有归类为一个变量,则E的暂时局部变量类型被创建并且E的值被分配给 变量。 E然后被重新分类为对该临时局部变量的参考。临时变量可以在 M之内访问,但不能以其他任何方式访问。因此,只有当E是真变量什么是真变量??),呼叫者是否有可能观察到M对此做出的更改。

埃里克利珀接着说:

这一点说明了另一种方式,其中 可变性的复制值语义的结合,可能会导致麻烦。例如,对于 示例,在运行构建器之后,只读字段未被分类为变量。因此,试图调用 值类型的只读字段的内容的方法成功,但实际上 会变更副本!通过完全避免可变值类型 来避免这些问题。

如何重现Eric描述的scenerio?我尝试了以下。它的错误了,我会想到:

struct A 
    { 
     public readonly int mutableReadonlyField; 

     public A(int originalValue) 
     { 
      mutableReadonlyField = originalValue; 
     } 

     public A MethodThatMutatesTheContentsOfAReadOnlyField(int mutate) 
     {    
      this.mutableReadonlyField = mutate;//Constructor has run so mutableReadonlyField is a temporary local variable 
      //ERROR: A readonly field cannot be assigned to (except in a constructor or a variable initializer) 

      A newA = this;//Is this a true variable? 
      return newA; 
     } 
} 

回答

4

我给我的博客上这样的例子:

http://ericlippert.com/2008/05/14/mutating-readonly-structs/

的问题是,我的句子片段“值类型的只读字段”是含糊不清和误导性的。我希望它意味着类别中的只读字段,其中字段为值类型S,但显然更自然的读数是将其作为S本身的只读字段。我应该完全重写这个句子。抱歉的错误。

要回答你的其他问题:形容词“真”是不必要的。如果它只是说“因此,只有当E是变量时,句子才会同样正确,因此调用者可能会观察到M对此做出的更改。”

+0

在我看来,一般而言,只读和可变类型是一个错误的组合 – 2013-02-19 16:20:21

+1

@ P.Brian.Mackey:正确这是一个更一般规则的特殊情况,即X和可变类型对X的所有值都是一个不好的组合。 – 2013-02-19 17:40:45

相关问题