gob/datetime/range.go

123 lines
3.8 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package datetime
import (
"time"
. "gitea.zaclys.com/bvaudour/gob/option"
)
// Range représente une période entre deux dates.
type Range struct {
begin time.Time
end time.Time
}
// NewRange initialise une période.
// Si t1 > t2, la date début de la période sera t2, et inversement si t1 < t2.
func NewRange(t1, t2 time.Time) Range {
if Gt(t1, t2) {
t1, t2 = t2, t1
}
return Range{
begin: t1,
end: t2,
}
}
// Begin retourne la date de début de la période.
func (r Range) Begin() time.Time { return r.begin }
// End retourne la date de fin de la période.
func (r Range) End() time.Time { return r.end }
// BeforeDate retourne vrai si la date est située avant la période.
func (r Range) BeforeDate(t time.Time) bool { return Lt(r.end, t) }
// AfterDate retourne vrai si la date est située après la période.
func (r Range) AfterDate(t time.Time) bool { return Gt(r.begin, t) }
// ContainsDate retourne vrai si t ∈ [begin; end].
func (r Range) ContainsDate(t time.Time) bool { return Le(r.begin, t) && Ge(r.end, t) }
// ContainsDateStrictBegin retourne vrai si t ∈ ]begin; end].
func (r Range) ContainsDateStrictBegin(t time.Time) bool { return Lt(r.begin, t) && Ge(r.end, t) }
// ContainsDateStrictEnd retourne vrai si t ∈ [begin; end[.
func (r Range) ContainsDateStrictEnd(t time.Time) bool { return Le(r.begin, t) && Gt(r.end, t) }
// ContainsDateStrict retourne vrai si t ∈ ]begin; end[.
func (r Range) ContainsDateStrict(t time.Time) bool { return Lt(r.begin, t) && Gt(r.end, t) }
// IsFuture retourne vrai si la période est située dans le futur.
func (r Range) IsFuture() bool { return r.AfterDate(time.Now()) }
// IsPast retourne vrai si la période est située dans le passé.
func (r Range) IsPast() bool { return r.BeforeDate(time.Now()) }
// IsNow retourne vrai si la période est en cours.
func (r Range) IsNow() bool { return r.ContainsDate(time.Now()) }
// Before retourne vrai si r est avant r2 sans la recouvrir.
func (r Range) Before(r2 Range) bool { return Le(r.end, r2.begin) }
// After retourne vrai si r est après r2 sans la recouvrir.
func (r Range) After(r2 Range) bool { return Ge(r.begin, r2.end) }
// Contains retourne vrai si r inclut complètement r2.
func (r Range) Contains(r2 Range) bool { return Le(r.begin, r2.begin) && Ge(r.end, r2.end) }
// In retourne vrai si r est complètement inclus dans r2.
func (r Range) In(r2 Range) bool { return r2.Contains(r) }
// Excludes retourne vrai si les périodes ne se chevauchent pas.
func (r Range) Excludes(r2 Range) bool { return Le(r.end, r2.begin) || Ge(r.begin, r2.end) }
// Overlaps retourne vrai si les périodes se chevauchent.
func (r Range) Overlaps(r2 Range) bool { return Lt(r.begin, r2.end) && Gt(r.end, r2.begin) }
// Intersection retourne la période commune aux deux périodes, si elle existe.
func (r Range) Intersection(r2 Range) (result Option[Range]) {
if r.Overlaps(r2) {
result = Some(NewRange(Max(r.begin, r2.begin), Min(r.end, r2.end)))
}
return
}
// Joins retourne la plus grande période contiguë entre deux période, si elle existe.
func (r Range) Joins(r2 Range) (result Option[Range]) {
if Le(r.begin, r2.end) && Ge(r.end, r2.begin) {
result = Some(NewRange(Min(r.begin, r2.begin), Max(r.end, r2.end)))
}
return
}
// Diff retourne lensemble des périodes non communes aux deux périodes.
func (r Range) Diff(r2 Range) (result []Range) {
if Ne(r.begin, r2.begin) {
begin := Min(r.begin, r2.begin)
var end time.Time
if begin == r.begin {
end = Min(r.end, r2.begin)
} else {
end = Min(r2.end, r.begin)
}
result = append(result, NewRange(begin, end))
}
if Ne(r.end, r2.end) {
end := Max(r.end, r2.end)
var begin time.Time
if end == r.end {
begin = Max(r.begin, r2.end)
} else {
begin = Max(r2.begin, r.end)
}
result = append(result, NewRange(begin, end))
}
return
}