Weekday Calculator

Miscellaneous programs and scripts, opensource or not, and sometimes, random mathematical stuff.
Post Reply
Gamall
Hic sunt dracones
Posts: 4174
Joined: Fri May 26, 2006 11:09 pm
Contact:

Weekday Calculator

Post by Gamall »

My first O'Caml program... doesn't everybody need a weekday calculator ? :lol
weekday.zip
(245.66 KiB) Downloaded 1365 times

Code: Select all

{===============================================================}
{                      Weekday Calculator                       }
{---------------------------------------------------------------}
{                 Author: Gamall Wednesday Ida                  }
{                  Mail: gamall.ida@gmail.com                   }
{                      Web: gamall-ida.com                      }
{===============================================================}
 
 
 
{===============================================================}
{                         What is it ?                          }
{===============================================================}
 
 
 This  program  computes  how  much  time has elapsed between two
 dates, and which day of  the  week  a  specific  date  is.  Most
 programs  doing  that kind of thing only support a limited range
 of dates, like years 1700-3000 or so. This is not the case here:
 dates are supported well beyond the  range  where  our  calendar
 makes sense.                                                    
 
 
{===============================================================}
{                       How do I use it ?                       }
{===============================================================}
 
 
 The  help  text,  displayed  when  the  program  is  run without
 arguments, covers it all:                                       
 
      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~      
       
       **  Weekday Calculator
       **  by Gamall Wednesday Ida
       **  email : gamall.ida@gmail.com
       **  web   : gamall-ida.com
       
       Usage :
       
       ./weekday -day <day> <month> <year>
       > returns day of the week
       
       ./weekday -ela <d1> <m1> <y1> <d2> <m2> <y2>
       > returns days elapsed betweed two dates
       
       Example:
       
       ./weekday -day 21 10 1985             --> Monday
       ./weekday -ela 1   1 1900  21 10 1985 --> 31339
       
      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~      
 
 
{===============================================================}
{                          Running it                           }
{===============================================================}
 
 
 This program has been written in O'Caml. It is in fact  my  very
 first  program  in  this language. A 'Hello World', so to speak,
 but I release it because it can actually  be  mildly  useful  :P
 Three files are provided :                                      
 
 -> 'weekday' : Linux executable, compiled under Ubuntu 7.04.    
                                                                 
 -> 'weekday.exe' : Windows executable. Will run fine under Linux
 with Wine.                                                      
                                                                 
 -> 'weekday.bytecode' : OCaml universal bytecode. Will run on   
 any platform with ocamlrun.                                     
                                                                 
 The  source  code, 'weekday.ml', is also shipped. It is released
 under   the   GNU   General    Public    License.    See    here
 <http://www.gnu.org/copyleft/gpl.html>   for  more  information.
 
 
{===============================================================}
{                          END OF FILE                          }
{===============================================================}
 
 




























  +-----------------------------+
  | File generated with 'GaTeX',|
  | an ASCII typesetting system |
  | by  Gamall  Wednesday  Ida. |
  |   http://gamall-ida.com     |
  +-----------------------------+
  Build: Wed Oct 24 21:31:07 2007
  File : f:readme.GaTeX.source

Code: Select all

(* 
     Weekday Calculator 
	by Gamall Wednesday Ida
	gamall-ida.com

     Note: This is my very first O'Caml program :-))
*)

(* numerical date *)
type date = int * int * int ;;

let getDay = function
    d, m, y -> d;;

let getMonth = function
    d, m, y -> m;;

let getYear = function
    d, m, y -> y;;
 
(* Day pretty print *)
let printDay = function
    0 -> "Monday"
  | 1 -> "Tuesday"
  | 2 -> "Wednesday"
  | 3 -> "Thursday"
  | 4 -> "Friday"
  | 5 -> "Saturday"
  | 6 -> "Sunday"
  | _ -> failwith "Error: trying to print out-of bounds weekday !";;

(* is this year a leap year ? *)
let isLeap y = 
  ((y mod 4 = 0) & (y mod 100 <> 0)) || (y mod 400 = 0);;

(* how many days in this specific month ? *)
let daysInMonth m y = match m with
  | 1 | 3 | 5 | 7 | 8 | 10 | 12 -> 31
  | 2 -> if isLeap y then 29 else 28
  | _ when (m <= 12 & m > 0) -> 30
  | _ -> failwith("Error : Incorrect month !");;

(* how many days in this year ? *)
let daysInYear y = if isLeap y then 366 else 365;;

(* is this date valid ? *)
let isValid adate =
  let d = getDay adate and m = getMonth adate and y = getYear adate in
     d > 0 & m > 0 & m <= 12 & d <= daysInMonth m y ;;

(* is a date strictly anterior to another ? *)
let ( << ) d dd = 
  let cy =  getYear d < getYear dd and cm = getMonth d < getMonth dd and cd = getDay d < getDay dd in
    cy || (getYear d = getYear dd & cm) || ( (getYear d = getYear dd) & (getMonth d = getMonth dd) & cd );;

(* get next day *)
let succ = function
    d, m, y when isValid (d+1, m, y) -> d+1, m, y
  | d, m, y when isValid (1, m+1, y) -> 1, m+1, y
  | d, m, y -> 1, 1, y+1;;

(* what's my position in this year ? *)
let rec posInYear = function
  |0, 0, y -> 0
  |31,12,y -> daysInYear y
  |0, m, y -> (daysInMonth m y) + posInYear (0, m-1, y)
  |d, m, y -> d + posInYear (0, m-1, y);;
  
(* how many days between two dates ? *)
let rec elapsed d dd =
  if d = dd then 0 else
    if dd << d then (- elapsed dd d) else 
      let rec ie d dd acc =
	if d = dd then acc else
	  if getYear dd > getYear d then ie d (31, 12, (getYear dd) - 1) (acc + (posInYear dd)) else
	    ie (succ d) dd (acc+1)
      in
	ie (succ d) dd 1 ;;


(* which day of the week is this date ? *)
let dayOfWeek adate =
  let n = (elapsed (21, 10,1985) adate ) mod 7 in
    if n < 0 then printDay (n+7) else
      printDay n;;

(*************************************************************)

open Printf

let av = Sys.argv;;
let ac = Array.length av;;

let _ =
  if ac = 1 then (
    printf "\n**  Weekday Calculator\n";
    printf "**  by Gamall Wednesday Ida\n";
    printf "**  email : gamall.ida@gmail.com\n";
    printf "**  web   : gamall-ida.com\n\n";
    
    printf "Usage :\n\n";
    printf "%s -day <day> <month> <year>\n" av.(0);
    printf "> returns day of the week\n\n";

    printf "%s -ela <d1> <m1> <y1> <d2> <m2> <y2>\n" av.(0);
    printf "> returns days elapsed betweed two dates\n\n";

    printf "Example:\n\n";
    printf "%s -day 21 10 1985             --> Monday\n" av.(0);
    printf "%s -ela 1   1 1900  21 10 1985 --> 31339\n\n" av.(0);
  ) else (
    if av.(1) = "-day" then (
      if ac <> 5 then failwith "ERROR: Incorrect number of arguments !";

      let da = (int_of_string av.(2), int_of_string av.(3), int_of_string av.(4)) in (
          if not (isValid da) then failwith "ERROR: Invalid date !";
	  printf "%s\n" (dayOfWeek da);
	);
    )else if av.(1) = "-ela" then (
      if ac <> 8 then failwith "ERROR: Incorrect number of arguments !";

      let da = (int_of_string av.(2), int_of_string av.(3), int_of_string av.(4)) and
	  db = (int_of_string av.(5), int_of_string av.(6), int_of_string av.(7)) in (
          if (not (isValid da) || not (isValid db)) then failwith "ERROR: Invalid date !";
	  printf "%d\n" (elapsed da db);
	);

    ) else failwith "ERROR: Unrecognized command !";
  )
;;
{<§ Gamall Wednesday Ida §>}
{ Mods and Programs - Mods TES-IV Oblivion }
Kafou
Poulidor Gnomonique
Posts: 1526
Joined: Sun Aug 19, 2007 7:17 pm
Location: dans son labo
Contact:

Re: Weekday Calculator

Post by Kafou »

Ca ne prend pas en compte les dates précédant le 20/12/1582 (en se limitant au cas de la France, sinon bonjour pour les cas particuliers, palme pour la Suède et son 30 février 1712).

Et le calcul des années bissextiles n'est pas valable pour les années avant Jésus-Christ.

Ca reconnait même l'année 0, qui n'a jamais existé !

Donc c'est nul.

:P
Gamall
Hic sunt dracones
Posts: 4174
Joined: Fri May 26, 2006 11:09 pm
Contact:

Re: Weekday Calculator

Post by Gamall »

D'où le
dates are supported well beyond the range where our calendar makes sense.
Et toc :foufou
{<§ Gamall Wednesday Ida §>}
{ Mods and Programs - Mods TES-IV Oblivion }
Post Reply

Who is online

Users browsing this forum: No registered users and 249 guests