Browse Source

init

master
3136352472 4 years ago
parent
commit
a9d46e1d8f
  1. 2
      .gitignore
  2. 212
      core.go
  3. 310
      core_test.go

2
.gitignore

@ -11,4 +11,4 @@
# Output of the go coverage tool, specifically when used with LiteIDE
*.out
.idea

212
core.go

@ -0,0 +1,212 @@
package time_arrow
import (
"errors"
"fmt"
"log"
"sort"
"strings"
"time"
)
type TimeArrowType string
const (
TimeArrowTypeDayOfWeek TimeArrowType = "DAY_OF_WEEK"
TimeArrowTypeDayOfMonth TimeArrowType = "DAY_OF_MONTH"
TimeArrowTypeDateSlice TimeArrowType = "DATE_SLICE"
)
type DateSlice struct {
Start string `json:"start"`
End string `json:"end"`
}
type TimeArrow struct {
Id int `json:"id"`
Group string `json:"group"`
Type TimeArrowType `json:"type"`
//可选
DayOfWeek []int `json:"day_of_week"`
DayOfMonth []int `json:"day_of_month"`
DateSlice []DateSlice `json:"date_slice"`
//必选
TimesOnDay []string `json:"times_on_day"`
ExpandTags []string `json:"expand_tags"`
ExpandValue interface{} `json:"expand_value"`
Weights float64 `json:"weights"`
}
type TimeArrows []TimeArrow
var GetData = func(group string) (TimeArrows, error) {
return nil, errors.New("GetData 未实现")
}
func isInDateSlice(t time.Time, ta TimeArrow) bool {
for e := range ta.DateSlice {
startStr := ta.DateSlice[e].Start
startSc := strings.Split(startStr, " ")
if len(startSc) < 2 {
startSc = append(startSc, "00:00:00")
} else {
startSc[1] = timeCompletion(startSc[1])
}
startStr = strings.Join(startSc, " ")
endStr := ta.DateSlice[e].End
endSc := strings.Split(endStr, " ")
if len(endSc) < 2 {
endSc = append(endSc, "00:00:00")
} else {
endSc[1] = timeCompletion(endSc[1])
}
endStr = strings.Join(endSc, " ")
startTime, err := time.Parse("2006-01-02 15:04:05", startStr)
if err != nil {
log.Println("时间段开始时间格式错误", startStr)
continue
}
endTime, err := time.Parse("2006-01-02 15:04:05", endStr)
if err != nil {
log.Println("时间段结束时间格式错误", startStr)
continue
}
if startTime.Unix() > endTime.Unix() {
log.Println("开始时间必须小于结束时间", startStr, endStr)
continue
}
if t.After(startTime) && t.Before(endTime) {
return true
}
}
return false
}
func isInWeekOfDay(t time.Time, ta TimeArrow) bool {
nowWeekInt := int(t.Weekday())
for k := range ta.DayOfWeek {
if ta.DayOfWeek[k] == nowWeekInt {
return true
}
}
return false
}
func timeCompletion(a string) string {
sc := strings.Split(a, ":")
for len(sc) < 3 {
sc = append(sc, "00")
}
return strings.Join(sc, ":")
}
func isInDayOfMonth(t time.Time, ta TimeArrow) bool {
day := t.Day()
for e := range ta.DayOfMonth {
if ta.DayOfMonth[e] == day {
return true
}
}
return false
}
func isInTimeOfDay(t time.Time, ta TimeArrow) bool {
if len(ta.TimesOnDay) == 0 {
return true
}
for k := range ta.TimesOnDay {
tsp := strings.Split(ta.TimesOnDay[k], "-")
if len(tsp) < 2 {
log.Println("必须为时间段:", ta.TimesOnDay[k])
continue
}
start, end := tsp[0], tsp[1]
start = timeCompletion(start)
end = timeCompletion(end)
startTime, err := time.Parse("2006-01-02 15:04:05", fmt.Sprintf("%s %s", t.Format("2006-01-02"), start))
if err != nil {
log.Println("时间段开始时间格式错误", start)
continue
}
endTime, err := time.Parse("2006-01-02 15:04:05", fmt.Sprintf("%s %s", t.Format("2006-01-02"), end))
if err != nil {
log.Println("时间段结束时间格式错误", end)
continue
}
if startTime.Unix() > endTime.Unix() {
log.Println("开始时间必须小于结束时间", end)
continue
}
if t.After(startTime) && t.Before(endTime) {
return true
}
}
return false
}
func isInExpandTags(ta TimeArrow, expandTag string) bool {
if len(ta.ExpandTags) == 0 {
return true
}
for e := range ta.ExpandTags {
if ta.ExpandTags[e] == expandTag {
return true
}
}
return false
}
func GetHitTimeArrow(t time.Time, group string, expandTags ...string) (*TimeArrow, error) {
ta, err := GetData(group)
if err != nil {
return nil, err
}
sort.Slice(ta, func(i, j int) bool {
return ta[i].Weights > ta[j].Weights
})
for e := range ta {
//当天具体时间判断
if !isInTimeOfDay(t, ta[e]) {
continue
}
//扩展标签判断
if !isInExpandTags(ta[e], strings.Join(expandTags, "-")) {
continue
}
switch ta[e].Type {
case TimeArrowTypeDayOfWeek:
//一周中某一天是否判定
if isInWeekOfDay(t, ta[e]) {
return &ta[e], nil
}
break
case TimeArrowTypeDayOfMonth:
//一月中某一天是否判定
if isInDayOfMonth(t, ta[e]) {
return &ta[e], nil
}
break
case TimeArrowTypeDateSlice:
//一月中某一天是否判定
if isInDateSlice(t, ta[e]) {
return &ta[e], nil
}
break
default:
log.Println("类型错误:", ta[e].Type)
}
}
return nil, nil
}

310
core_test.go

@ -0,0 +1,310 @@
package time_arrow
import (
"testing"
"time"
)
func Test_isInWeekOfDay(t *testing.T) {
ti, err := time.Parse("2006-01-02 15:04:05", "2020-06-08 00:00:00")
if err != nil {
panic(err)
}
ok := isInWeekOfDay(ti, TimeArrow{
DayOfWeek: []int{
1,
3,
},
})
if !ok {
t.Fatal("error")
}
ok = isInWeekOfDay(ti, TimeArrow{
DayOfWeek: []int{
6,
3,
2,
},
})
if ok {
t.Fatal("error")
}
ok = isInWeekOfDay(ti, TimeArrow{})
if ok {
t.Fatal("error")
}
}
func Test_timeCompletion(t *testing.T) {
if timeCompletion("12") != "12:00:00" {
t.Fatal("error")
}
if timeCompletion("17:00") != "17:00:00" {
t.Fatal("error")
}
}
func Test_isInTimeOfDay(t *testing.T) {
ti, err := time.Parse("2006-01-02 15:04:05", "2020-06-08 17:18:00")
if err != nil {
panic(err)
}
ok := isInTimeOfDay(ti, TimeArrow{
TimesOnDay: []string{
"1:21",
"1:21-2:22",
"17:00-18:00",
},
})
if !ok {
t.Fatal("error")
}
ok = isInTimeOfDay(ti, TimeArrow{
TimesOnDay: []string{
"17:00-17:10",
"18:00-19:00",
},
})
if ok {
t.Fatal("error")
}
}
func Test_isInDateSlice(t *testing.T) {
ti, err := time.Parse("2006-01-02 15:04:05", "2020-06-08 17:18:00")
if err != nil {
panic(err)
}
ok := isInDateSlice(ti, TimeArrow{
DateSlice: []DateSlice{},
})
if ok {
t.Fatal("error")
}
ok = isInDateSlice(ti, TimeArrow{
DateSlice: []DateSlice{
{
Start: "2020-06-05 17:18",
End: "2020-06-07",
},
},
})
if ok {
t.Fatal("error")
}
ok = isInDateSlice(ti, TimeArrow{
DateSlice: []DateSlice{
{
Start: "2020-06-05 17:18",
End: "2020-06-07",
},
{
Start: "2020-06-07 17:18",
End: "2020-06-09",
},
},
})
if !ok {
t.Fatal("error")
}
}
func Test_isInExpandTags(t *testing.T) {
ok := isInExpandTags(TimeArrow{
ExpandTags: []string{},
}, "一号场")
if !ok {
t.Fatal("error")
}
ok = isInExpandTags(TimeArrow{
ExpandTags: []string{
"一号场",
"二号场",
"四号场",
},
}, "一号场")
if !ok {
t.Fatal("error")
}
ok = isInExpandTags(TimeArrow{
ExpandTags: []string{
"一号场",
"二号场",
"四号场",
},
}, "三号场")
if ok {
t.Fatal("error")
}
}
func TestGetHitTimeArrow(t *testing.T) {
tas := TimeArrows{
{
Type: TimeArrowTypeDayOfWeek,
DayOfWeek: []int{
0,
1,
2,
3,
4,
5,
6,
},
ExpandTags: []string{
"一号场",
"二号场",
"三号场",
"四号场",
},
ExpandValue: 0,
Weights: 0,
},
{
Type: TimeArrowTypeDayOfWeek,
DayOfWeek: []int{
6,
0,
},
ExpandTags: []string{
"一号场",
"二号场",
"四号场",
},
ExpandValue: 30,
Weights: 1,
},
{
Type: TimeArrowTypeDayOfWeek,
DayOfWeek: []int{
6,
0,
},
ExpandTags: []string{
"三号场",
},
ExpandValue: 60,
Weights: 1,
},
{
Type: TimeArrowTypeDayOfMonth,
DayOfMonth: []int{
3,
5,
},
ExpandValue: 12,
Weights: 2,
},
{
Type: TimeArrowTypeDateSlice,
DateSlice: []DateSlice{
{
Start: "2020-04-05",
End: "2020-05-05",
},
{
Start: "2020-06-07 17:18",
End: "2020-06-09",
},
},
ExpandValue: 5,
Weights: 3,
},
{
Type: TimeArrowTypeDateSlice,
DateSlice: []DateSlice{
{
Start: "2020-04-05",
End: "2020-05-05",
},
{
Start: "2020-06-07 17:18",
End: "2020-06-09",
},
},
TimesOnDay: []string{
"18-19",
},
ExpandValue: 180,
Weights: 4,
},
}
GetData = func(group string) (arrows TimeArrows, e error) {
return tas, nil
}
ti, err := time.Parse("2006-01-02 15:04:05", "2020-06-01 17:18:00")
if err != nil {
panic(err)
}
result, err := GetHitTimeArrow(ti, "", "一号场")
if err != nil || result == nil {
t.Fatal("error")
panic(err)
}
if result.ExpandValue.(int) != 0 {
t.Fatal("error")
}
ti = ti.AddDate(0, 0, -1)
result, err = GetHitTimeArrow(ti, "", "一号场")
if err != nil || result == nil {
t.Fatal("error")
panic(err)
}
if result.ExpandValue.(int) != 30 {
t.Fatal("error", result.ExpandValue.(int))
}
result, err = GetHitTimeArrow(ti, "", "三号场")
if err != nil || result == nil {
t.Fatal("error")
panic(err)
}
if result.ExpandValue.(int) != 60 {
t.Fatal("error")
}
ti, err = time.Parse("2006-01-02 15:04:05", "2020-04-11 17:18:00")
if err != nil {
panic(err)
}
result, err = GetHitTimeArrow(ti, "", "三号场")
if err != nil || result == nil {
t.Fatal("error")
panic(err)
}
if result.ExpandValue.(int) != 5 {
t.Fatal("error")
}
ti = ti.Add(time.Hour)
result, err = GetHitTimeArrow(ti, "", "三号场")
if err != nil || result == nil {
t.Fatal("error")
panic(err)
}
if result.ExpandValue.(int) != 180 {
t.Fatal("error")
}
}
Loading…
Cancel
Save