Skip to content

Instantly share code, notes, and snippets.

@isaacabraham
Created December 19, 2021 18:31
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save isaacabraham/e74ccb69cee86112eee7148ec59d27e4 to your computer and use it in GitHub Desktop.
Save isaacabraham/e74ccb69cee86112eee7148ec59d27e4 to your computer and use it in GitHub Desktop.
#r "nuget:FSCheck"
open FsCheck
open System
type TurnDirection = Left | Right
type MoveDirection = Forward | Back
type Direction = N | S | E | W
type Coordinates = { X : int; Y : int }
type State =
{
Facing : Direction
Position : Coordinates
}
let changeDirection turn facing =
match facing, turn with
| N, Left -> W
| S, Left -> E
| E, Left -> N
| W, Left -> S
| N, Right -> E
| S, Right -> W
| E, Right -> S
| W, Right -> N
let rotate turn state =
{ state with Facing = state.Facing |> changeDirection turn }
let move direction state =
{ state with
Position =
match state.Facing, direction with
| N, Forward -> { state.Position with Y = state.Position.Y + 1 }
| S, Forward -> { state.Position with Y = state.Position.Y - 1 }
| E, Forward -> { state.Position with X = state.Position.X + 1 }
| W, Forward -> { state.Position with X = state.Position.X - 1 }
| S, Back -> { state.Position with Y = state.Position.Y + 1 }
| N, Back -> { state.Position with Y = state.Position.Y - 1 }
| W, Back -> { state.Position with X = state.Position.X + 1 }
| E, Back -> { state.Position with X = state.Position.X - 1 }
}
let moveInDirectionAlwaysChangesPos turn state =
let newState = state |> rotate turn |> move Forward
newState <> state
let twoDifferentDirectionsNeverGiveSameResult state =
let stateLeft = state |> rotate Left |> move Forward
let stateRight = state |> rotate Right |> move Forward
stateLeft <> stateRight
let onlyEverMovesOneSquare turn state =
let newState = state |> rotate turn |> move Forward
newState.Position.X - state.Position.X |> Math.Abs < 2
&& newState.Position.Y - state.Position.Y |> Math.Abs < 2
let movingForwardIsTwoAwayFromBack turn state =
let fwd = state |> rotate turn |> move Forward
let back = state |> rotate turn |> move Back
fwd.Position.X - back.Position.X |> Math.Abs = 2 || fwd.Position.Y - back.Position.Y |> Math.Abs = 2
let backAndFwdOriginalResult turn state =
let endState =
state
|> rotate turn
|> move Back
|> move Forward
state.Position = endState.Position
let northForwardAlwaysMovesUp startPosition =
let newState = { Facing = N; Position = startPosition } |> move Forward
newState.Position.Y = startPosition.Y + 1
Check.Quick moveInDirectionAlwaysChangesPos
Check.Quick twoDifferentDirectionsNeverGiveSameResult
Check.Quick onlyEverMovesOneSquare
Check.Quick movingForwardIsTwoAwayFromBack
Check.Quick backAndFwdOriginalResult
Check.Quick northForwardAlwaysMovesUp
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment