github.com/matrixorigin/matrixone@v0.7.0/pkg/vectorize/timediff/timediff.go (about) 1 // Copyright 2022 Matrix Origin 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package timediff 16 17 import ( 18 "github.com/matrixorigin/matrixone/pkg/container/types" 19 ) 20 21 type DiffT interface { 22 types.Time | types.Datetime 23 } 24 25 func TimeDiffWithTimeFn[T DiffT](v1, v2 []T, rs []types.Time) error { 26 if len(v1) == 1 && len(v2) == 1 { 27 for i := 0; i < len(rs); i++ { 28 res, err := timeDiff(v1[0], v2[0]) 29 if err != nil { 30 return err 31 } 32 rs[0] = res 33 } 34 } else if len(v1) == 1 { 35 for i := 0; i < len(rs); i++ { 36 res, err := timeDiff(v1[0], v2[i]) 37 if err != nil { 38 return err 39 } 40 rs[i] = res 41 } 42 } else if len(v2) == 1 { 43 for i := 0; i < len(rs); i++ { 44 res, err := timeDiff(v1[i], v2[0]) 45 if err != nil { 46 return err 47 } 48 rs[i] = res 49 } 50 } else { 51 for i := 0; i < len(rs); i++ { 52 res, err := timeDiff(v1[i], v2[i]) 53 if err != nil { 54 return err 55 } 56 rs[i] = res 57 } 58 } 59 return nil 60 } 61 62 func timeDiff[T DiffT](v1, v2 T) (types.Time, error) { 63 tmpTime := int64(v1 - v2) 64 // different sign need to check over flow 65 if (int64(v1)>>63)^(int64(v2)>>63) != 0 { 66 if (tmpTime>>63)^(int64(v1)>>63) != 0 { 67 // overflow 68 isNeg := int64(v1) < 0 69 return types.TimeFromClock(isNeg, types.MaxHourInTime, 59, 59, 0), nil 70 } 71 } 72 73 // same sign don't need to check overflow 74 time := types.Time(tmpTime) 75 hour, _, _, _, isNeg := time.ClockFormat() 76 if !types.ValidTime(uint64(hour), 0, 0) { 77 return types.TimeFromClock(isNeg, types.MaxHourInTime, 59, 59, 0), nil 78 } 79 return time, nil 80 }