Ich habe einen Typ namens Cube, der einen physischen Würfel darstellt. Ich habe einen Code geschrieben, der einen Würfel nimmt und eine Liste aller möglichen Orientierungen des Würfels erzeugt.Gibt es eine schönere Möglichkeit, alle möglichen Orientierungen eines Würfels in F # zu berechnen?
Ich habe die folgende Terminologie verwendet, vorausgesetzt, der Würfel sitzt auf Augenhöhe vor mir.
Für die Gesichter der Würfel:
- Die Oberseiten der Decke.
- Der Boden steht dem Tisch gegenüber.
- Die Vorderseite ist von mir abgewandt.
- Die Rückseite steht mir gegenüber.
- Die linke Seite der Wand links von mir.
- Das Recht steht zu der Wand rechts von mir. erstreckt sich von dem Tisch an der Decke
- der normalen Achse:
für die Achsen kann der Würfel herum gedreht werden.
- Die Längsachse erstreckt sich von mir zur Wand vor mir.
- Die Querachse erstreckte sich von der linken Wand bis zur rechten Wand.
Während jede der 6 Flächen bleibt nach unten zeigt, kann der Würfel um seine Hochachse 4 verschiedene Möglichkeiten (0, 90, 180 und 270 Grad) gedreht werden. Dies ergibt 24 mögliche Orientierungen.
Ich habe mit dem Cube-Typ gestartet (bitte entschuldigen S/O Syntaxcoloring):
type 'a cube(top:'a, bottom:'a, left:'a, right:'a, front:'a, back:'a) =
member this.Top = top
member this.Bottom = bottom
member this.Left = left
member this.Right = right
member this.Front = front
member this.Back = back
override this.ToString() =
sprintf "Top: %O, Bottom: %O, Left: %O, Right: %O Front: %O, Back: %O" top bottom left right front back
I, die die Funktion getOrientations vorgesehen ging dann auf eine Cube-Modul zu schreiben.
module Cube =
let rotateNormalRight (c:'a cube) =
cube(c.Top, c.Bottom, c.Back, c.Front, c.Left, c.Right)
let rotateLongitudinalRight (c:'a cube) =
cube(c.Left, c.Right, c.Bottom, c.Top, c.Front, c.Back)
let rotateLongitudinalLeft (c:'a cube) =
cube(c.Right, c.Left, c.Top, c.Bottom, c.Front, c.Back)
let private operations =
[ rotateNormalRight; rotateNormalRight; rotateNormalRight; rotateLongitudinalRight
rotateNormalRight; rotateNormalRight; rotateNormalRight; rotateLongitudinalRight
rotateNormalRight; rotateNormalRight; rotateNormalRight; rotateLongitudinalLeft
rotateNormalRight; rotateNormalRight; rotateNormalRight; rotateLongitudinalLeft
rotateNormalRight; rotateNormalRight; rotateNormalRight; rotateLongitudinalRight
rotateNormalRight; rotateNormalRight; rotateNormalRight ]
let getOrientations startCube =
let rec getCubeInner (ops:('a cube -> 'a cube) list) (cl:'a cube list) =
match ops with
| [] -> cl
| op :: rest -> getCubeInner rest ((cl |> List.hd |> op) :: cl)
getCubeInner operations [startCube]
Dieses Modul liefert nur drei mögliche 90-Grad-Drehungen, eine Liste von Umdrehungen, die einen Würfel durch jede mögliche Ausrichtung nehmen, und eine Funktion, die einen einzigen Würfel gegeben, alle Orientierungen erzeugt.
Wenn ich tun:
cube(1, 2, 3, 4, 5, 6)
|> Cube.getOrientations
|> List.iter (printfn "%O")
ich:
Top: 3, Bottom: 4, Left: 1, Right: 2 Front: 6, Back: 5
Top: 3, Bottom: 4, Left: 6, Right: 5 Front: 2, Back: 1
Top: 3, Bottom: 4, Left: 2, Right: 1 Front: 5, Back: 6
Top: 3, Bottom: 4, Left: 5, Right: 6 Front: 1, Back: 2
Top: 6, Bottom: 5, Left: 3, Right: 4 Front: 1, Back: 2
Top: 6, Bottom: 5, Left: 1, Right: 2 Front: 4, Back: 3
Top: 6, Bottom: 5, Left: 4, Right: 3 Front: 2, Back: 1
Top: 6, Bottom: 5, Left: 2, Right: 1 Front: 3, Back: 4
Top: 2, Bottom: 1, Left: 5, Right: 6 Front: 3, Back: 4
Top: 2, Bottom: 1, Left: 3, Right: 4 Front: 6, Back: 5
Top: 2, Bottom: 1, Left: 6, Right: 5 Front: 4, Back: 3
Top: 2, Bottom: 1, Left: 4, Right: 3 Front: 5, Back: 6
Top: 4, Bottom: 3, Left: 1, Right: 2 Front: 5, Back: 6
Top: 4, Bottom: 3, Left: 5, Right: 6 Front: 2, Back: 1
Top: 4, Bottom: 3, Left: 2, Right: 1 Front: 6, Back: 5
Top: 4, Bottom: 3, Left: 6, Right: 5 Front: 1, Back: 2
Top: 5, Bottom: 6, Left: 4, Right: 3 Front: 1, Back: 2
Top: 5, Bottom: 6, Left: 1, Right: 2 Front: 3, Back: 4
Top: 5, Bottom: 6, Left: 3, Right: 4 Front: 2, Back: 1
Top: 5, Bottom: 6, Left: 2, Right: 1 Front: 4, Back: 3
Top: 1, Bottom: 2, Left: 5, Right: 6 Front: 4, Back: 3
Top: 1, Bottom: 2, Left: 4, Right: 3 Front: 6, Back: 5
Top: 1, Bottom: 2, Left: 6, Right: 5 Front: 3, Back: 4
Top: 1, Bottom: 2, Left: 3, Right: 4 Front: 5, Back: 6
Das tut, was ich will. Aber das Cube-Modul wird von dieser riesigen Liste von Operationen übernommen.
Gibt es einen besseren Weg, dies mit vielleicht weniger Operationen oder einem völlig anderen Ansatz zu tun?
Als Referenz haben Würfel in diesen Tagen eine besondere Eigenschaft: jede Seite und ihre gegenüberliegende Seite summieren sich zu 7. – cHao
@cHao: In der Tat - deshalb habe ich den Begriff Würfel verwendet - ich denke, ich wäre mit einzelnen Zeichen besser dran gewesen eher für die Frage als für ganze Zahlen. –
Und nicht "Würfel" im Namen einer Ihrer Funktionen verwenden. :) – cHao