Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Various Date/Time fixes #20226

Merged
merged 12 commits into from
Jan 28, 2017
Prev Previous commit
Next Next commit
Whitespace fixes for dates code
  • Loading branch information
quinnj committed Jan 26, 2017
commit 760e8596c0b7f68eb0a6f42ea6459fee0b129ce9
59 changes: 30 additions & 29 deletions base/dates/accessors.jl
Original file line number Diff line number Diff line change
Expand Up @@ -3,62 +3,63 @@
# Convert # of Rata Die days to proleptic Gregorian calendar y,m,d,w
# Reference: http:https://mysite.verizon.net/aesir_research/date/date0.htm
function yearmonthday(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
d = c - div(153m-457,5); return m > 12 ? (y+1,m-12,d) : (y,m,d)
z = days + 306; h = 100z - 25; a = fld(h, 3652425); b = a - fld(a, 4)
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
d = c - div(153m - 457, 5); return m > 12 ? (y + 1, m - 12, d) : (y, m, d)
end
function year(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
return m > 12 ? y+1 : y
z = days + 306; h = 100z - 25; a = fld(h, 3652425); b = a - fld(a, 4)
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
return m > 12 ? y + 1 : y
end
function yearmonth(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
return m > 12 ? (y+1,m-12) : (y,m)
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
return m > 12 ? (y + 1, m - 12) : (y, m)
end
function month(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
return m > 12 ? m-12 : m
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
return m > 12 ? m - 12 : m
end
function monthday(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
d = c - div(153m-457,5); return m > 12 ? (m-12,d) : (m,d)
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
d = c - div(153m - 457, 5); return m > 12 ? (m - 12, d) : (m, d)
end
function day(days)
z = days + 306; h = 100z - 25; a = fld(h,3652425); b = a - fld(a,4)
y = fld(100b+h,36525); c = b + z - 365y - fld(y,4); m = div(5c+456,153)
return c - div(153m-457,5)
y = fld(100b + h, 36525); c = b + z - 365y - fld(y, 4); m = div(5c + 456, 153)
return c - div(153m - 457, 5)
end
# https://en.wikipedia.org/wiki/Talk:ISO_week_date#Algorithms
const WEEK_INDEX = (15, 23, 3, 11)
function week(days)
w = div(abs(days-1),7) % 20871
c,w = divrem((w + (w >= 10435)),5218)
w = (w*28+[15,23,3,11][c+1]) % 1461
return div(w,28) + 1
w = div(abs(days - 1), 7) % 20871
c, w = divrem((w + (w >= 10435)), 5218)
w = (w * 28 + WEEK_INDEX[c + 1]) % 1461
return div(w, 28) + 1
end

# Accessor functions
value(dt::TimeType) = dt.instant.periods.value
value(t::Time) = t.instant.value
days(dt::Date) = value(dt)
days(dt::DateTime) = fld(value(dt),86400000)
days(dt::DateTime) = fld(value(dt), 86400000)
year(dt::TimeType) = year(days(dt))
month(dt::TimeType) = month(days(dt))
week(dt::TimeType) = week(days(dt))
day(dt::TimeType) = day(days(dt))
hour(dt::DateTime) = mod(fld(value(dt),3600000),24)
minute(dt::DateTime) = mod(fld(value(dt),60000),60)
second(dt::DateTime) = mod(fld(value(dt),1000),60)
millisecond(dt::DateTime) = mod(value(dt),1000)
hour(t::Time) = mod(fld(value(t),3600000000000),Int64(24))
minute(t::Time) = mod(fld(value(t),60000000000),Int64(60))
second(t::Time) = mod(fld(value(t),1000000000),Int64(60))
millisecond(t::Time) = mod(fld(value(t),Int64(1000000)),Int64(1000))
microsecond(t::Time) = mod(fld(value(t),Int64(1000)),Int64(1000))
nanosecond(t::Time) = mod(value(t),Int64(1000))
hour(dt::DateTime) = mod(fld(value(dt), 3600000), 24)
minute(dt::DateTime) = mod(fld(value(dt), 60000), 60)
second(dt::DateTime) = mod(fld(value(dt), 1000), 60)
millisecond(dt::DateTime) = mod(value(dt), 1000)
hour(t::Time) = mod(fld(value(t), 3600000000000), Int64(24))
minute(t::Time) = mod(fld(value(t), 60000000000), Int64(60))
second(t::Time) = mod(fld(value(t), 1000000000), Int64(60))
millisecond(t::Time) = mod(fld(value(t), Int64(1000000)), Int64(1000))
microsecond(t::Time) = mod(fld(value(t), Int64(1000)), Int64(1000))
nanosecond(t::Time) = mod(value(t), Int64(1000))

dayofmonth(dt::TimeType) = day(dt)

Expand Down
32 changes: 16 additions & 16 deletions base/dates/adjusters.jl
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ The step size in adjusting can be provided manually through the `step` keyword.
`limit` provides a limit to the max number of iterations the adjustment API will
pursue before throwing an error (given that `f::Function` is never satisfied).
"""
function Date(func::Function, y, m=1, d=1;step::Period=Day(1), negate=nothing, limit::Int=10000)
function Date(func::Function, y, m=1, d=1; step::Period=Day(1), negate=nothing, limit::Int=10000)
func = deprecate_negate(:Date, func, "func,y,m,d", negate)
return adjust(DateFunction(func, Date(y, m, d)), Date(y, m, d), step, limit)
end
Expand Down Expand Up @@ -197,10 +197,10 @@ function DateTime(func::Function, y, m, d, h, mi, s; step::Period=Millisecond(1)
end

"""
Time(func::Function, h, mi=0; step::Period=Second(1), negate::Bool=false, limit::Int=10000)
Time(func::Function, h, mi, s; step::Period=Millisecond(1), negate::Bool=false, limit::Int=10000)
Time(func::Function, h, mi, s, ms; step::Period=Microsecond(1), negate::Bool=false, limit::Int=10000)
Time(func::Function, h, mi, s, ms, us; step::Period=Nanosecond(1), negate::Bool=false, limit::Int=10000)
Time(func::Function, h, mi=0; step::Period=Second(1), limit::Int=10000)
Time(func::Function, h, mi, s; step::Period=Millisecond(1), limit::Int=10000)
Time(func::Function, h, mi, s, ms; step::Period=Microsecond(1), limit::Int=10000)
Time(func::Function, h, mi, s, ms, us; step::Period=Nanosecond(1), limit::Int=10000)

Create a `Time` through the adjuster API. The starting point will be constructed from the
provided `h, mi, s, ms, us` arguments, and will be adjusted until `f::Function` returns `true`.
Expand Down Expand Up @@ -240,51 +240,51 @@ ISDAYOFWEEK = Dict(Mon => DateFunction(ismonday, Date(0)),

# "same" indicates whether the current date can be considered or not
"""
tonext(dt::TimeType,dow::Int;same::Bool=false) -> TimeType
tonext(dt::TimeType, dow::Int; same::Bool=false) -> TimeType

Adjusts `dt` to the next day of week corresponding to `dow` with `1 = Monday, 2 = Tuesday,
etc`. Setting `same=true` allows the current `dt` to be considered as the next `dow`,
allowing for no adjustment to occur.
"""
tonext(dt::TimeType, dow::Int; same::Bool=false) = adjust(ISDAYOFWEEK[dow], same ? dt : dt+Day(1), Day(1), 7)
tonext(dt::TimeType, dow::Int; same::Bool=false) = adjust(ISDAYOFWEEK[dow], same ? dt : dt + Day(1), Day(1), 7)

# Return the next TimeType where func evals true using step in incrementing
"""
tonext(func::Function,dt::TimeType;step=Day(1),limit=10000,same=false) -> TimeType
tonext(func::Function, dt::TimeType; step=Day(1), limit=10000, same=false) -> TimeType

Adjusts `dt` by iterating at most `limit` iterations by `step` increments until `func`
returns `true`. `func` must take a single `TimeType` argument and return a `Bool`. `same`
allows `dt` to be considered in satisfying `func`.
"""
function tonext(func::Function, dt::TimeType;step::Period=Day(1), negate=nothing, limit::Int=10000, same::Bool=false)
function tonext(func::Function, dt::TimeType; step::Period=Day(1), negate=nothing, limit::Int=10000, same::Bool=false)
func = deprecate_negate(:tonext, func, "func,dt", negate)
return adjust(DateFunction(func, dt), same ? dt : dt+step, step, limit)
return adjust(DateFunction(func, dt), same ? dt : dt + step, step, limit)
end

"""
toprev(dt::TimeType,dow::Int;same::Bool=false) -> TimeType
toprev(dt::TimeType, dow::Int; same::Bool=false) -> TimeType

Adjusts `dt` to the previous day of week corresponding to `dow` with `1 = Monday, 2 =
Tuesday, etc`. Setting `same=true` allows the current `dt` to be considered as the previous
`dow`, allowing for no adjustment to occur.
"""
toprev(dt::TimeType, dow::Int; same::Bool=false) = adjust(ISDAYOFWEEK[dow], same ? dt : dt+Day(-1), Day(-1), 7)
toprev(dt::TimeType, dow::Int; same::Bool=false) = adjust(ISDAYOFWEEK[dow], same ? dt : dt + Day(-1), Day(-1), 7)

"""
toprev(func::Function,dt::TimeType;step=Day(-1),limit=10000,same=false) -> TimeType
toprev(func::Function, dt::TimeType; step=Day(-1), limit=10000, same=false) -> TimeType

Adjusts `dt` by iterating at most `limit` iterations by `step` increments until `func`
returns `true`. `func` must take a single `TimeType` argument and return a `Bool`. `same`
allows `dt` to be considered in satisfying `func`.
"""
function toprev(func::Function, dt::TimeType; step::Period=Day(-1), negate=nothing, limit::Int=10000, same::Bool=false)
func = deprecate_negate(:toprev, func, "func,dt", negate)
return adjust(DateFunction(func, dt), same ? dt : dt+step, step, limit)
return adjust(DateFunction(func, dt), same ? dt : dt + step, step, limit)
end

# Return the first TimeType that falls on dow in the Month or Year
"""
tofirst(dt::TimeType,dow::Int;of=Month) -> TimeType
tofirst(dt::TimeType, dow::Int; of=Month) -> TimeType

Adjusts `dt` to the first `dow` of its month. Alternatively, `of=Year` will adjust to the
first `dow` of the year.
Expand All @@ -296,7 +296,7 @@ end

# Return the last TimeType that falls on dow in the Month or Year
"""
tolast(dt::TimeType,dow::Int;of=Month) -> TimeType
tolast(dt::TimeType, dow::Int; of=Month) -> TimeType

Adjusts `dt` to the last `dow` of its month. Alternatively, `of=Year` will adjust to the
last `dow` of the year.
Expand Down
14 changes: 7 additions & 7 deletions base/dates/conversions.jl
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,15 @@ Converts a `DateTime` to a `Date`. The hour, minute, second, and millisecond par
the `DateTime` are truncated, so only the year, month and day parts are used in
construction.
"""
Date(dt::TimeType) = convert(Date,dt)
Date(dt::TimeType) = convert(Date, dt)

"""
DateTime(dt::Date) -> DateTime

Converts a `Date` to a `DateTime`. The hour, minute, second, and millisecond parts of
the new `DateTime` are assumed to be zero.
"""
DateTime(dt::TimeType) = convert(DateTime,dt)
DateTime(dt::TimeType) = convert(DateTime, dt)

"""
Time(dt::DateTime) -> Time
Expand All @@ -27,7 +27,7 @@ the `DateTime` are used to create the new `Time`. Microsecond and nanoseconds ar
"""
Time(dt::DateTime) = convert(Time, dt)

Base.convert(::Type{DateTime}, dt::Date) = DateTime(UTM(value(dt)*86400000))
Base.convert(::Type{DateTime}, dt::Date) = DateTime(UTM(value(dt) * 86400000))
Base.convert(::Type{Date}, dt::DateTime) = Date(UTD(days(dt)))
Base.convert(::Type{Time}, dt::DateTime) = Time(Nanosecond((value(dt) % 86400000) * 1000000))

Expand Down Expand Up @@ -55,7 +55,7 @@ end
Takes the given `DateTime` and returns the number of seconds
since the unix epoch `1970-01-01T00:00:00` as a `Float64`.
"""
datetime2unix(dt::DateTime) = (value(dt) - UNIXEPOCH)/1000.0
datetime2unix(dt::DateTime) = (value(dt) - UNIXEPOCH) / 1000.0

"""
now() -> DateTime
Expand All @@ -66,7 +66,7 @@ locale.
function now()
tv = Libc.TimeVal()
tm = Libc.TmStruct(tv.sec)
return DateTime(tm.year+1900,tm.month+1,tm.mday,tm.hour,tm.min,tm.sec,div(tv.usec,1000))
return DateTime(tm.year + 1900, tm.month + 1, tm.mday, tm.hour, tm.min, tm.sec, div(tv.usec, 1000))
end

"""
Expand Down Expand Up @@ -99,7 +99,7 @@ Returns the number of Rata Die days since epoch from the given `Date` or `DateTi
datetime2rata(dt::TimeType) = days(dt)

# Julian conversions
const JULIANEPOCH = value(DateTime(-4713,11,24,12))
const JULIANEPOCH = value(DateTime(-4713, 11, 24, 12))

"""
julian2datetime(julian_days) -> DateTime
Expand All @@ -118,4 +118,4 @@ end
Takes the given `DateTime` and returns the number of Julian calendar days since the julian
epoch `-4713-11-24T12:00:00` as a `Float64`.
"""
datetime2julian(dt::DateTime) = (value(dt) - JULIANEPOCH)/86400000.0
datetime2julian(dt::DateTime) = (value(dt) - JULIANEPOCH) / 86400000.0
Loading