funcprog: finished week 2, assignment 5.{1,2,3}.

parent a97f3667
(*
* Check if the given year is a leap year. This will return true if the given
* integer is larger than 1582, can be divided by 4, but not by 100, or it can
* be divided by 400. Otherwise, false is returned.
*)
let isLeapYear x = let isLeapYear x =
x >= 1582 && x mod 4 == 0 && (x mod 100 != 0 || x mod 400 == 0) x > 1582 && x mod 4 == 0 && (x mod 100 != 0 || x mod 400 == 0)
;; ;;
let testLeapYear x = let testLeapYear x =
Printf.printf "%4d: %b\n" x (isLeapYear x);; Printf.printf "%d: %b\n" x (isLeapYear x);;
(testLeapYear 1400);; (* false *) (testLeapYear 1400);; (* false *)
(testLeapYear 1582);; (* false *) (testLeapYear 1582);; (* false *)
......
(*
* Implementation of date2str.
*
* Given a correct calendar triple (day, month, year), return a proper English
* date. For example: (1, 2, 2011) returns "February 1st, 2011".
*
* The suffix of the day number is not related to the actual month, so "February
* 31st, 2011" can be generated. However, there is no reason to implement error
* checking to prevent returning unvalid day/month combinations (not part of the
* assignment). Note: the assigment clearly states that a correct calendar
* triple is the input of date2str.
*
* This implementation does check for invalid day numbers or invalid month
* numbers. The exception Hell will be raised for these invalid integers.
*)
exception Hell exception Hell
(*
* Given a day number, return the day number followed by its English suffix. For
* example, this will return ``1st'' for day 1, ``23rd'' for day 23 and ``12th'
* for day 12. If the day number is negative or the day number is not between 1
* and 31 (inclusive), Hell will be raised.
*)
let day_with_suffix day = let day_with_suffix day =
match day with match day with
1 | 21 | 31 -> (string_of_int day) ^ "st" 1 | 21 | 31 -> (string_of_int day) ^ "st"
| 2 | 22 -> (string_of_int day) ^ "nd" | 2 | 22 -> (string_of_int day) ^ "nd"
| 3 | 23 -> (string_of_int day) ^ "rd" | 3 | 23 -> (string_of_int day) ^ "rd"
| _ when day > 0 -> (string_of_int day) ^ "th" | _ when (day > 0 && day < 32) -> (string_of_int day) ^ "th"
| _ -> raise Hell | _ -> raise Hell
;; ;;
(*
* Return the English name of a month number (a number between 1 and 12,
* inclusive). If the month number is not defined, Hell will be raised.
*)
let month_name month = let month_name month =
match month with match month with
1 -> "January" 1 -> "January"
......
let rec digitRoot number = (*
let result = ref 0 in * Calculate the digital root of a number: add up all of its digits, and do that
let current = ref number in ( * recursively until a single digit is obtained.
Printf.printf "input: %d\n" !current; *)
while !current > 0 do let rec digitRoot ?(sum=0) number = match number with
result := !result + (!current mod 10); _ when number < 10 -> (sum + number)
Printf.printf "%d + " (!current mod 10); | _ -> (digitRoot (digitRoot ~sum:(sum + (number mod 10)) (number / 10)))
current := !current / 10;
done;
Printf.printf "= %d\n" !result;
if !result > 9 then
(digitRoot !result)
else
!result
)
;; ;;
let test_digitRoot input = let test_digitRoot input =
...@@ -23,8 +13,11 @@ let test_digitRoot input = ...@@ -23,8 +13,11 @@ let test_digitRoot input =
Printf.printf "%d -> %d\n" input (digitRoot input) Printf.printf "%d -> %d\n" input (digitRoot input)
;; ;;
(test_digitRoot 20);; test_digitRoot 20;;
(test_digitRoot 24);; test_digitRoot 24;;
(test_digitRoot 1234);; test_digitRoot 1234;; (* = 1 *)
(test_digitRoot 123456789);; test_digitRoot 65536;; (* = 7 *)
(test_digitRoot (-1));; (* what to do with negative numbers? *) test_digitRoot 12345678;; (* = 9 *)
test_digitRoot 18273645;; (* = 9 *)
test_digitRoot 123456789;; (* = 9 *)
test_digitRoot 5674;; (* = 4 *)
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment