solve_2.ml 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. open Stdio
  2. open Str
  3. let rec construct_list l1=
  4. let line = In_channel.input_line In_channel.stdin in
  5. match line with
  6. | None -> l1
  7. | Some x -> let report = List.map int_of_string (Str.split (regexp {| |}) x) in
  8. construct_list (report::l1)
  9. ;;
  10. let monotony a b = if ((abs (a - b)) < 4) then
  11. (if (a < b) then "increasing" else
  12. (if (a > b) then "decreasing" else "ko"))
  13. else "ko"
  14. ;;
  15. let rec is_safe status tolerance prev_element l =
  16. if (tolerance < 0) then false else
  17. (match status with
  18. | "ko" -> (match l with
  19. | a :: b :: tl -> (is_safe (monotony prev_element a) (tolerance - 1) 0 (prev_element::b::tl)) ||
  20. (is_safe (monotony a b) (tolerance - 1) 0 (b::tl))
  21. | _ :: [] | [] -> true)
  22. | "increasing" -> (match l with
  23. | a :: b :: tl -> (if ((monotony a b) == "increasing") then (is_safe "increasing" tolerance a (b::tl))
  24. else ((is_safe "increasing" (tolerance-1) 0 (prev_element::b::tl)) ||
  25. (is_safe "increasing" (tolerance-1) 0 (a::tl))))
  26. | _ :: [] | [] -> true)
  27. | "decreasing" -> (match l with
  28. | a :: b :: tl -> (if ((monotony a b) == "decreasing") then (is_safe "decreasing" tolerance a (b::tl))
  29. else ((is_safe "decreasing" (tolerance-1) 0 (prev_element::b::tl)) ||
  30. (is_safe "decreasing" (tolerance-1) 0 (a::tl))))
  31. | _ :: [] | [] -> true)
  32. | "confirm_monotony" -> (match l with
  33. | a :: b :: tl -> let initial_monotonity = (monotony prev_element a) in
  34. let current_monotonity = (monotony a b) in
  35. let is_foul = (if initial_monotonity == current_monotonity then 0 else 1) in
  36. (is_safe current_monotonity (tolerance - is_foul) a (a::tl)) ||
  37. (is_safe initial_monotonity (tolerance - is_foul) a (prev_element::b::tl))
  38. | _ :: [] | [] -> true)
  39. | "init" -> (match l with
  40. | a :: b :: tl -> is_safe (if ((a == b) || (abs(a - b) >= 4)) then "ko" else "confirm_monotony") tolerance a (b::tl)
  41. | _ :: [] | [] -> true)
  42. | _ -> true )
  43. ;;
  44. let rec solve accum = function
  45. | hd :: tl -> if (is_safe "init" 1 0 hd) then solve (accum + 1) tl else solve accum tl
  46. | [] -> accum
  47. ;;
  48. let () =
  49. let li = construct_list [] in
  50. printf "Total: %d\n" (solve 0 li)