-
Notifications
You must be signed in to change notification settings - Fork 0
/
dates.ex
39 lines (32 loc) · 870 Bytes
/
dates.ex
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
defmodule Dates do
@doc """
reads an ISO date string ("yyyy-mm-dd") and converts it to a list of numbers
"""
@spec date_part(String.t :: list
def date_part(str) do
Enum.map(String.split(str,"-"), fn s -> String.to_integer(s) end)
end
@doc """
reads an ISO date string ("yyyy-mm-dd") and converts it to a Julian date (1-365))
"""
@spec julian(String.t) :: number
def julian(str) do
[y, m, d] = date_part(str)
julian(y, m-1, d)
end
defp julian(_, 1, d), do: d+31
defp julian(y, m, d) do
julian(y, m-1, d+days_in_month(y, m))
end
defp days_in_month(y, m) do
cond do
m == 9 || m == 4 || m == 6 || m == 11
-> 30
2 -> if is_leap_year(y), do: 29, else: 28
true -> 31
end
end
defp is_leap_year(y) do
(rem(y,4) == 0 and rem(y,100) != 0) or (rem(y, 400) == 0)
end
end