Dir*_*oer 7 c# syntax immutability
我经常遇到小型不可变数据结构的需求.其他人可能会在这些情况下使用Tuples,但我真的不喜欢Tuples不能很好地阅读并且没有表达那么多意义.一Value2中int并没有告诉我任何事情.
一个例子是为两个属性的组合创建一个查找表(Dictionary),即Name和Rating.
为我知道的这些案例制作不可变结构的最短方法是:
public struct Key
{
public string Name { get; private set; }
public int Rating { get; private set; }
public LolCat(string name, int rating) : this()
{
Name = name;
Rating = rating;
}
}
// useage
var key = new Key( "MonorailCat", 5 );
Run Code Online (Sandbox Code Playgroud)
在我看来,这里仍有很多"语法脂肪",我想摆脱它.当我直接暴露字段时,我可以使它更具可读性.
public struct Key
{
public string Name;
public int Rating;
}
// useage
var key = new Key { Name = "MonorailCat", Rating = 5 };
Run Code Online (Sandbox Code Playgroud)
我非常喜欢这种语法,因为几乎没有任何语法上的脂肪.当然,最大的缺点是它不是一成不变的,具有所有危险.
在理想的情况下,我只想有一个特殊的类型,真正的最低定义,如:
public immutable struct Key
{
string Name;
int Rating;
}
// useage (needs compiler magic)
var key = new Key( Name: "MonorailCat", Rating: 5 );
Run Code Online (Sandbox Code Playgroud)
题
是否有一个真实世界的解决方案更接近于底部的示例,以减少非常简单的不可变结构的语法脂肪量?
Jon*_*eet 15
从C#6开始,您可以编写相当紧凑的struct初始值设定项:
public struct Key
{
public string Name { get; }
public int Rating { get; }
public Key(string name, int rating)
{
this.Name = name;
this.Rating = rating;
}
}
Run Code Online (Sandbox Code Playgroud)
......至少要短得多.我强烈建议IEquatable<Key>您实施,请注意.
请注意,当您处理结构时,您仍然可以编写:
Key key = new Key();
Console.WriteLine(key.Rating); // 0
Run Code Online (Sandbox Code Playgroud)
......这可能不是问题,但通常至少需要考虑.
在C#6之前,我实际上要比当前代码更长,以便将属性写为只读属性:
public struct Key
{
private readonly string name;
private readonly int rating;
public string Name { get { return name; } }
public int Rating { get { return rating; } }
public Key(string name, int rating)
{
this.name = name;
this.rating = rating;
}
}
Run Code Online (Sandbox Code Playgroud)
我觉得这使得它更清楚地"意味着不可改变" - 如果你有一个可写的财产,即使这个设定者只是私人的,也不能传达IMO的正确印象.(虽然值得注意的是结构中的不变性总是有点假装,因为你可以分配给this成员......)