使用对象初始化程序语法的操作顺序

Mic*_*cah 28 .net syntax object-initializers

使用对象初始化程序语法设置属性的顺序是否以完全相同的顺序执行?

例如,如果我这样做:

var s = new Person { FirstName = "Micah",
                     LastName = "Martin",
                     IsLoaded = true
                   }
Run Code Online (Sandbox Code Playgroud)

每个属性都会以相同的顺序设置吗?

Jon*_*eet 45

是.

中断的道歉(我必须经常做一些工作).该规范没有明确说明,但它在第7.6.10.2节中使IMO非常清楚:


对象初始值设定项由一系列成员初始值设定项组成,由{和}标记括起并用逗号分隔.

(注意这里的"序列"这个词,而不是"set".我个人认为这很重要,因为序列是有序的.)

以下类表示具有两个坐标的点:

public class Point
{
    int x, y;
    public int X { get { return x; } set { x = value; } }
    public int Y { get { return y; } set { y = value; } }
}
Run Code Online (Sandbox Code Playgroud)

可以创建Point的实例并初始化如下:

Point a = new Point { X = 0, Y = 1 };
Run Code Online (Sandbox Code Playgroud)

效果与...相同

Point __a = new Point();
__a.X = 0;
__a.Y = 1; 
Point a = __a;
Run Code Online (Sandbox Code Playgroud)

其中__a是一个不可见且无法访问的临时变量.


编辑:我收到了Mads Torgersen的回复,他基本上已经说过现在可以做的任何事情都会保留订单.将来可能会有一些奇怪的地方,在你做除了设置属性/字段之外的其他事情的情况下,订单不会被保留,但这取决于语言的去向.

值得指出的是,这里实际上有很多步骤 - 执行参数评估的顺序(即RHS位)和赋值的执行顺序.例如,如果您有:

new Foo
{
    A = X,
    B = Y
}
Run Code Online (Sandbox Code Playgroud)

在保持实际属性执行(A和B)的顺序的同时,所有以下命令都是可能的:

  • 评估X,分配给A,评估Y,分配给B
  • 评估X,评估Y,分配给A,分配给B.
  • 评估Y,评估X,分配给A,分配给B

我相信第一个选项是实际使用的选项,但这只是为了证明它不仅仅是满足于眼睛.

我也非常谨慎地编写依赖于此的代码...

  • 你是参考. (3认同)
  • 唔。就我而言,我的担忧恰恰相反。分配顺序对我来说非常无关紧要,因为我只需要初始化对象/结构。然而,评估的顺序很重要,因为我使用 BinaryReader 并且每个字段都是由 ReadSingle() 调用设置的。如果不能保证顺序,我最好完全避免使用对象初始值设定项。安全总比后悔好。如果没有正确指定,这样的语法糖是毫无用处的^^。实际上是否存在未保留评估令的记录案例? (3认同)
  • 我最关心的是分配按照我列出的顺序发生。我并不关心右侧的求值顺序,而是关心实际的左侧分配顺序。 (2认同)
  • @Bunny83:我不知道,而且我非常有信心*保留*,这就是规范的意图 - 它只是不像它可能的那样明确。 (2认同)