Advertisement
Guest User

Untitled

a guest
Dec 17th, 2017
61
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
OCaml 2.90 KB | None | 0 0
  1. (* Origami
  2.    Autor : Michał Kardaś
  3.    Reviewer : ?
  4. *)
  5.  
  6. type point = float * float
  7.  
  8. type kartka = point -> int
  9.  
  10. let eps = 1e-9
  11.  
  12. let meps = -1e-9
  13.  
  14. (* iloczyn skalarny wektora <ab> i <ac> *)
  15. let skal (ax ,ay) (bx ,by) (cx ,cy) =
  16.   (cx -. ax) *. (bx -. ax) +. (cy -. ay) *. (by -. ay)
  17.  
  18. (* zakłada, że a!=b
  19.    punkt rzutowania punktu c na prostę wyznaczoną przez punkty a i b *)
  20. let punkt_rzutowania a b c =
  21.   let (ax ,ay) = a and
  22.   (bx ,by) = b  in
  23.   (* ze wzorku wynika, że f jest stosunkiem |ax| do |ac| gdzie
  24.      x jest rzutem punktu c na prostą wyznaczoną przez punkty a b *)
  25.   let f = skal a b c /. skal a b b  
  26.   in (ax +. f *. (bx -. ax), ay +. f *. (by -. ay))
  27.  
  28. (* iloczny wektorowy wektora <ab> i <ac>
  29.    dodatni jeżeli c lezy po lewej stronie idąc od a do b *)
  30. let det (ax ,ay) (bx ,by) (cx ,cy) =
  31.   (bx -. ax) *. (cy -. ay) -. (by -. ay) *. (cx -. ax)
  32.  
  33. let sgn x =
  34.   if x < meps then -1
  35.   else if x > eps then 1 else 0
  36.  
  37. (* po ktorej stronie prostej idąc od a do b leży c
  38.    1 - lewej
  39.    0 - leży na prostej
  40.    -1 - prawej *)
  41. let strona a b c =
  42.   sgn (det a b c)
  43.  
  44. (* zakłada, że a i b są przyczepione do przecięcia osi współrzędnych
  45.    zwraca wektor od konca a do konca b *)
  46. let roznica (ax ,ay) (bx ,by) =
  47.   (ax -. bx ,ay -. by)
  48.  
  49. (* zakłada, że a i b są przyczepione do przecięcia osi współrzędnych
  50.    zwraca sumę wektorów *)
  51. let suma (ax ,ay) (bx ,by) =
  52.   (bx +. ax ,ay +. by)
  53.  
  54. (* odbicie punktu c względem prostej wyznaczonej przez punkty a i b *)
  55. let odbicie a b c =
  56.   let rzut = punkt_rzutowania a b c in
  57.     suma rzut (roznica rzut c)
  58.  
  59. (* kwadrat odległości punktów a i b *)
  60. let odl (ax ,ay) (bx ,by) =
  61.   (ax -. bx) *. (ax -. bx) +. (ay -. by) *. (ay -. by)
  62.  
  63. let prostokat (ax ,ay) (bx ,by) =
  64.   fun (cx ,cy) -> if (cx -. bx) < eps && (ax -. cx) < eps &&
  65.                      (cy -. by) < eps && (ay -. cy) < eps
  66.     then 1 else 0
  67.  
  68. (* jeżeli kwadrat odległości środka i punktu a jest mniejszy niż
  69.    kwadrat promienia + eps to a należy do kółka *)
  70. let kolko a r =
  71.   fun c -> if odl a c -. (r *. r) < eps then 1 else 0
  72.  
  73. let zloz a b kartka =
  74.   fun c -> let po_ktorej = strona a b c in
  75.       (* jezeli po_ktorej = 1 to c leży na lewo od prostej wyznaczonej
  76.          przez punkty a i b więc istnieje niezerowa szansa na to, że
  77.          jakiś punkt z kartki po prawej stronie na niego przeszedł, więc
  78.          dla odbitego punktu jak i punktu c zliczamy wystąpienia w
  79.          poprzednich złożeniach kartki *)
  80.       if po_ktorej = 1
  81.       then kartka c + kartka (odbicie a b c)
  82.       (* punkt c leży na prostej, więc nie zanika ani nie rozbija się *)
  83.       else if po_ktorej = 0
  84.       then kartka c
  85.       (* leży po prawej stronie złożenia, więc pomijamy *)
  86.       else 0
  87.  
  88. (* składanie funkcji zloz w sposob podany w treści *)
  89. let skladaj l k =
  90.   List.fold_left (fun acc (x ,y) -> zloz x y acc) k l
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement