如果主要目的之一是能够执行重做/撤消,我不会使用委托引用作为旋转建模的方式。我会考虑为每次旋转创建一个数据模型,并存储这些旋转步骤的列表。然后,每个步骤都可以有它自己的关联重做/撤消委托,它允许遍历列表的人(从任一端)了解发生了哪些操作,并重复或反转它们。
对此类转换进行建模的面向数据的方法的另一个好处是,它可能会减少方法的相似(但略有不同)版本的数量RotateXXX( )
。
编辑:解决您关于这种解决方案可能采取何种形式的问题。
最简单的做法可能是将Tuple<Action,Action>
代表每对旋转/取消旋转操作的 a 存储为成对的委托。但是,我会考虑使用描述旋转操作的显式数据结构,可能最终包括描述性名称、方向/面属性等。我还将更改您的RotateXXX
方法,使其成为 的静态方法Cube
,并接受多维数据集的实例作为参数。这将允许在 的实例外部对旋转操作进行建模Cube
。
public sealed class Rotation
{
private readonly Action<Cube> _RotateAction;
private readonly Action<Cube> _UnrotateAction; // used for undo or backtracking
private Rotation( Action<Cube> rotateAction, Action<Cube> unrotateAction )
{
_RotateAction = rotateAction;
_UnrotateAction = unrotateAction;
}
public void Rotate( Cube cube ) { _RotateAction( cube ); }
public void Unrotate( Cube cube ) { _Unrotate( cube ); }
public static readonly RotateFrontFaceClockswise =
new Rotation( Cube.RotateFrontFaceClockwise
Cube.RotateFrontFaceCounterClockwise );
public static readonly RotateFrontFaceCounterClockwise =
new Rotation( Cube.RotateFrontFaceCounterClockwise,
Cube.RotateFrontFaceClockwise );
public static readonly RotateLeftFaceClockwise =
new Rotation( Cube.RotateLeftFaceClockwise,
Cube.RotateLeftFaceCounterClockwise );
public static readonly RotateLeftFaceCounterClockwise =
new Rotation( Cube.RotateLeftFaceCounterClockwise,
Cube.RotateLeftFaceClockwise );
// etc..
}
// now we can keep track of the state changes of a cube using:
List<Rotation> cubeRotations = new List<Rotation>();
cubeRotations.Add( Rotation.RotateFrontFaceCounterClockwise );
cubeRotations.Add( Rotation.RotateBackFaceClockwise );
cubeRotations.Add( Rotation.RotateLeftFaceCounterClockwise );
// to apply the rotations to a cube, you simple walk through the data structure
// calling the Rotate( ) method on each:
Cube someCube = new Cube( ... )
foreach( Rotation r in cubeRotations )
{
r.Rotate( someCube );
}
// to undo these rotations you can walk the like in reverse:
foreach( Rotation r in cubeRotations.Reverse() )
{
r.Unrotate( someCube );
}