github.com/matrixorigin/matrixone@v0.7.0/pkg/container/nulls/nulls.go (about) 1 // Copyright 2021 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 nulls wrap up functions for the manipulation of bitmap library roaring. 16 // MatrixOne uses nulls to store all NULL values in a column. 17 // You can think of Nulls as a bitmap. 18 package nulls 19 20 import ( 21 "fmt" 22 "unsafe" 23 24 "github.com/matrixorigin/matrixone/pkg/common/bitmap" 25 ) 26 27 type Nulls struct { 28 Np *bitmap.Bitmap 29 } 30 31 func (n *Nulls) Clone() *Nulls { 32 if n == nil { 33 return nil 34 } 35 if n.Np == nil { 36 return &Nulls{Np: nil} 37 } 38 return &Nulls{ 39 Np: n.Np.Clone(), 40 } 41 } 42 43 // Or performs union operation on Nulls n,m and store the result in r 44 func Or(n, m, r *Nulls) { 45 if Ptr(n) == nil && Ptr(m) == nil { 46 r.Np = nil 47 return 48 } 49 50 r.Np = bitmap.New(0) 51 if Ptr(n) != nil { 52 r.Np.Or(n.Np) 53 } 54 if Ptr(m) != nil { 55 r.Np.Or(m.Np) 56 } 57 } 58 59 func Reset(n *Nulls) { 60 if n.Np != nil { 61 n.Np.Clear() 62 } 63 } 64 65 func NewWithSize(size int) *Nulls { 66 return &Nulls{ 67 Np: bitmap.New(size), 68 } 69 } 70 71 func Build(size int, rows ...uint64) *Nulls { 72 n := NewWithSize(size) 73 Add(n, rows...) 74 return n 75 } 76 77 // XXX this is so broken, 78 func New(n *Nulls, size int) { 79 n.Np = bitmap.New(size) 80 } 81 82 // Any returns true if any bit in the Nulls is set, otherwise it will return false. 83 func Any(n *Nulls) bool { 84 if n == nil || n.Np == nil { 85 return false 86 } 87 return !n.Np.IsEmpty() 88 } 89 90 func Ptr(n *Nulls) *uint64 { 91 if n == nil { 92 return nil 93 } 94 return n.Np.Ptr() 95 } 96 97 // Size estimates the memory usage of the Nulls. 98 func Size(n *Nulls) int { 99 if n.Np == nil { 100 return 0 101 } 102 return int(n.Np.Size()) 103 } 104 105 // Length returns the number of integers contained in the Nulls 106 func Length(n *Nulls) int { 107 if n.Np == nil { 108 return 0 109 } 110 return int(n.Np.Count()) 111 } 112 113 func String(n *Nulls) string { 114 if n.Np == nil { 115 return "[]" 116 } 117 return fmt.Sprintf("%v", n.Np.ToArray()) 118 } 119 120 func TryExpand(n *Nulls, size int) { 121 if n.Np == nil { 122 n.Np = bitmap.New(size) 123 return 124 } 125 n.Np.TryExpandWithSize(size) 126 } 127 128 // Contains returns true if the integer is contained in the Nulls 129 func Contains(n *Nulls, row uint64) bool { 130 return n != nil && n.Np != nil && n.Np.Contains(row) 131 } 132 133 func Add(n *Nulls, rows ...uint64) { 134 if len(rows) == 0 { 135 return 136 } 137 if n == nil { 138 n = &Nulls{} 139 } 140 TryExpand(n, int(rows[len(rows)-1])+1) 141 n.Np.AddMany(rows) 142 } 143 144 func AddRange(n *Nulls, start, end uint64) { 145 TryExpand(n, int(end+1)) 146 n.Np.AddRange(start, end) 147 } 148 149 func Del(n *Nulls, rows ...uint64) { 150 if n.Np == nil { 151 return 152 } 153 for _, row := range rows { 154 n.Np.Remove(row) 155 } 156 } 157 158 // Set performs union operation on Nulls n,m and store the result in n 159 func Set(n, m *Nulls) { 160 if m != nil && m.Np != nil { 161 if n.Np == nil { 162 n.Np = bitmap.New(0) 163 } 164 n.Np.Or(m.Np) 165 } 166 } 167 168 // FilterCount returns the number count that appears in both n and sel 169 func FilterCount(n *Nulls, sels []int64) int { 170 var cnt int 171 172 if n.Np == nil { 173 return cnt 174 } 175 if len(sels) == 0 { 176 return cnt 177 } 178 var sp []uint64 179 if len(sels) > 0 { 180 sp = unsafe.Slice((*uint64)(unsafe.Pointer(&sels[0])), cap(sels))[:len(sels)] 181 } 182 for _, sel := range sp { 183 if n.Np.Contains(sel) { 184 cnt++ 185 } 186 } 187 return cnt 188 } 189 190 func RemoveRange(n *Nulls, start, end uint64) { 191 if n.Np != nil { 192 n.Np.RemoveRange(start, end) 193 } 194 } 195 196 // Range adds the numbers in n starting at start and ending at end to m. 197 // `bias` represents the starting offset used for the Range Output 198 // Return the result 199 func Range(n *Nulls, start, end, bias uint64, m *Nulls) *Nulls { 200 switch { 201 case n.Np == nil && m.Np == nil: 202 case n.Np != nil && m.Np == nil: 203 m.Np = bitmap.New(int(end + 1 - bias)) 204 for ; start < end; start++ { 205 if n.Np.Contains(start) { 206 m.Np.Add(start - bias) 207 } 208 } 209 case n.Np != nil && m.Np != nil: 210 m.Np = bitmap.New(int(end + 1 - bias)) 211 for ; start < end; start++ { 212 if n.Np.Contains(start) { 213 m.Np.Add(start - bias) 214 } 215 } 216 } 217 return m 218 } 219 220 func Filter(n *Nulls, sels []int64) *Nulls { 221 if n.Np == nil { 222 return n 223 } 224 if len(sels) == 0 { 225 return n 226 } 227 var sp []uint64 228 if len(sels) > 0 { 229 sp = unsafe.Slice((*uint64)(unsafe.Pointer(&sels[0])), cap(sels))[:len(sels)] 230 } 231 np := bitmap.New(len(sels)) 232 upperLimit := uint64(n.Np.Len()) 233 for i, sel := range sp { 234 if sel >= upperLimit { 235 continue 236 } 237 if n.Np.Contains(sel) { 238 np.Add(uint64(i)) 239 } 240 } 241 n.Np = np 242 return n 243 } 244 245 func (n *Nulls) Any() bool { 246 if n == nil || n.Np == nil { 247 return false 248 } 249 return !n.Np.IsEmpty() 250 } 251 252 func (n *Nulls) Set(row uint64) { 253 TryExpand(n, int(row)+1) 254 n.Np.Add(row) 255 } 256 257 func (n *Nulls) Contains(row uint64) bool { 258 return n != nil && n.Np != nil && n.Np.Contains(row) 259 } 260 261 func (n *Nulls) Show() ([]byte, error) { 262 if n.Np == nil { 263 return nil, nil 264 } 265 return n.Np.Marshal(), nil 266 } 267 268 func (n *Nulls) Read(data []byte) error { 269 if len(data) == 0 { 270 return nil 271 } 272 n.Np = bitmap.New(0) 273 n.Np.Unmarshal(data) 274 return nil 275 } 276 277 func (n *Nulls) Or(m *Nulls) *Nulls { 278 switch { 279 case m == nil: 280 return n 281 case n.Np == nil && m.Np == nil: 282 return n 283 case n.Np != nil && m.Np == nil: 284 return n 285 case n.Np == nil && m.Np != nil: 286 return m 287 default: 288 n.Np.Or(m.Np) 289 return n 290 } 291 }