Advertisement
Guest User

Untitled

a guest
Feb 21st, 2019
62
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 1.17 KB | None | 0 0
  1. data Direction = Left | Right | Straight deriving (Show, Eq)
  2. type Coordinate = (Double, Double)
  3.  
  4. whichDirection :: Coordinate -> Coordinate -> Coordinate -> Direction
  5. whichDirection (x2, y2) (x1, y1) (x3, y3)
  6. | crossProduct == 0 = Straight
  7. | crossProduct > 0 = Right
  8. | crossProduct < 0 = Left
  9. where crossProduct = (x2 - x1)*(y3 - y1) - (y2 - y1)*(x3 - x1)
  10.  
  11. listDirection :: [Coordinate] -> [Direction]
  12. listDirection (a:b:c:xs) = (whichDirection a b c):(listDirection (b:c:xs))
  13. listDirection _ = []
  14.  
  15. grahamScan :: [Coordinate] -> [Coordinate]
  16. grahamScan ls@(a:b:c:xs) =
  17. let
  18. (pivot:rest) = sortBy (\ (x1, y1) (x2, y2) -> if y1 == y2 then compare x1 x2 else compare y1 y2) ls
  19. sortedRest = sortBy (compare `on` (angle pivot)) rest ++ [pivot]
  20. listOfDirections = listDirection $ sortedRest ++ [pivot]
  21. in
  22. [pivot] ++ (makeHull sortedRest listOfDirections)
  23. grahamScan _ = []
  24.  
  25. makeHull (a:b:c:xs) [] = [a]
  26. makeHull (a:b:c:xs) (dir:ds) =
  27. if dir == Right
  28. then a:(makeHull (c:xs) ds)
  29. else a:(makeHull (b:c:xs) ds)
  30. makeHull _ _ = []
  31.  
  32. angle (x1, y1) (x2, y2) = (dx / len, len) where
  33. dx = x1 - x2
  34. dy = y1 - y2
  35. len = sqrt (dx * dx + dy * dy)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement