vb.net与c#对象初始值设定项:c#中的限制

本文关键字:net 对象 vb | 更新日期: 2023-09-27 18:01:05

在VB.NET中,您可以使用对象初始值设定项并在右侧引用相同的成员,如下所示:

  GetValue.Add(New ArrayIndexInfo() With {
               .Type = CType(NvpInfo(Index), Type),
               .Name = NvpInfo(Index + 2).ToString,
               .NvpValues = CType(.Type.GetField(NvpInfo(Index + 1).ToString).GetValue(Instances.First(Function(o) o IsNot Nothing AndAlso o.GetType = CType(NvpInfo(Index), Type))), NameValuePair())
               })

请注意,在设置.NvpValues的行中,您可以引用.Type,这没有问题。

但是,如果你试图在c#中这样做(或者像我一样,尝试将一个项目从vb.net转换为c#(,你会得到一个错误。

<变量>未声明为

我这样处理它,这不是DRY,因为((Type)NvpInfo[Index])重复:

        functionReturnValue.Add(new ArrayIndexInfo {
            Type = (Type)NvpInfo[Index],
            Name = NvpInfo[Index + 2].ToString(),
            NvpValues = (NameValuePair[])((Type)NvpInfo[Index]).GetField(NvpInfo[Index + 1].ToString()).GetValue(Instances.First(o => o != null && o.GetType() == (Type)NvpInfo[Index]))
        });
  1. 为什么c#不允许这样做?我认为应该。我认为将遗留代码转换为c#应该尽可能轻松
  2. 有没有更好的方法可以绕过这个问题,仍然使用对象初始值设定项

vb.net与c#对象初始值设定项:c#中的限制

为了回答这个问题,我将以您的示例的简化版本为基础

VB.NET

Dim c = New SomeClass With {
    .Prop1 = "abc",
    .Prop2 = .Prop1
}
Console.WriteLine(c.Prop1) 'prints "abc"
Console.WriteLine(c.Prop2) 'prints "abc"

C#

var c = new SomeClass
{
    Prop1 = "abc",
    Prop2 = Prop1 // won't compile. Can't reference Prop1 here.
};
Console.WriteLine(c.Prop1);
Console.WriteLine(c.Prop2);

回答您的最后一个问题:

有没有更好的方法可以绕过这个问题,仍然使用对象初始值设定项?

因此,您担心的一个问题是,因为C#不允许在对象初始化语句中引用其他属性,这会导致您违反DRY原则。但实际上,你所需要做的就是使用变量:

不违反DRY原则的C#工作示例:

string temp = "abc";
var c = new SomeClass
{
    Prop1 = temp,
    Prop2 = temp
};
Console.WriteLine(c.Prop1); // prints "abc"
Console.WriteLine(c.Prop2); // prints "abc"

为什么c#不允许这样做?我认为应该。

显然,只有语言的设计者才能真正回答这个问题。但我至少可以分享为什么我更喜欢C#的设计决策。例如,在VB.NET版本中,如果我错误地以不同的顺序初始化属性:

Dim c = New SomeClass With {
    .Prop2 = .Prop1,
    .Prop1 = "abc"
}
Console.WriteLine(c.Prop1) 'prints "abc"
Console.WriteLine(c.Prop2) 'prints nothing

代码仍然是"合法的",但我现在无意中引入了一个错误,Prop2现在被错误地初始化了。

因为C#不允许这样做,所以它可以防止大多数与属性初始化顺序有关的错误。我同意,在这个非常简单的例子中,很难想象有人会犯这个错误。但是,对于更多的属性和更复杂的初始化语句,它可能不那么明显,而且更容易出错。C#可以帮助您避免这些微妙的错误。

我认为将遗留代码转换为c#应该尽可能轻松。

我猜你是在暗示VB.NET是一种遗留语言?有些人可能会生气:(

但更严重的是,你是否暗示应该做出语言设计决策来促进从其他语言的迁移?CCD_ 7和CCD_。它们并不意味着要有匹配和对称的语言设计。如果他们这样做了,那么拥有两种不同的语言又有什么意义呢?

没有。它们是两种不同的语言,有两种不同哲学。我们应该认为自己很幸运,移民之路和目前一样容易。没有理由需要它。