C#中的结构不';I don’我没有按预期工作

C#中的结构不';I don’我没有按预期工作,c#,struct,C#,Struct,我正在开发一个简单的应用程序,我有点困惑。我有一个带有intx和inty的简单struct点。我把它用于行 public class Line : Shape { public Line() { PointA = new Point(x: 0, y: 0); PointB = new Point(x: 0, y: 0); } public Point PointA { get; set; } public Point Point

我正在开发一个简单的应用程序,我有点困惑。我有一个带有
intx
inty
的简单
struct点。我把它用于

public class Line : Shape {

    public Line() {
        PointA = new Point(x: 0, y: 0);
        PointB = new Point(x: 0, y: 0);
    }

    public Point PointA { get; set; }
    public Point PointB { get; set; }
}
在某处

var line = new Line();
line.PointB = new Point(x: 4, y: 2);
Console.WriteLine($"Line start at {line.PointA.GetX()}:{line.PointA.GetY()}; end at {line.PointB.GetX()}:{line.PointB.GetY()}");

for (int i = 0; i < 10; i++) {
    line.PointB.IncrementX();
    line.PointB.IncrementY();
}
Console.WriteLine($"Line start at {line.PointA.GetX()}:{line.PointA.GetY()}; end at {line.PointB.GetX()}:{line.PointB.GetY()}");

Struct是一种值类型。并且它是通过值传递的(即通过创建所有字段的副本),而不是将引用传递给struct instance。所以当你这么做的时候

line.PointB.IncrementX()
调用PropertyB的getter时,它返回存储在PropertyB backing字段中的点的副本。然后在复制时调用increment。因此,原始值将保持不变

进一步阅读:尤其是

可变值类型是邪恶的。尝试始终创建值类型 不变的


如果要实际移动直线点,可以做什么

  • 将点类型更改为
    。然后它将通过引用传递,所有方法都将在存储在
    行中的原始点上调用

  • 将新的(修改的)点实例指定给直线

即,您应该存储副本、更改副本并重新分配

var point = line.PointB; // get copy
point.IncrementX();      // mutate copy
point.IncrementY();
line.PointB = point;     // assign copy of copy
您还可以使Point struct不可变(对于值类型您可以做的最好的事情):

现在改变位置看起来像

line.PointB = line.PointB.Move(1, 1);

point类是什么样子的?@SledgeHammer更新了,请查看可能的副本。您能稍微解释一下我应该怎么做吗,谢谢
public struct Point
{
    public Point(int x, int y)
    {
        X = x;
        Y = y;
    }

    public int X { get; }
    public int Y { get; }

    public Point IncrementX() => new Point(X + 1, Y);
    public Point IncrementY() => new Point(X, Y + 1);
    public Point Move(int dx, int dy) => new Point(X + dx, Y + dy);
}
line.PointB = line.PointB.Move(1, 1);