github.com/m3db/m3@v1.5.0/src/query/storage/m3/consolidators/fetch_result_map_wrapper.go (about)

     1  // Copyright (c) 2020 Uber Technologies, Inc.
     2  //
     3  // Permission is hereby granted, free of charge, to any person obtaining a copy
     4  // of this software and associated documentation files (the "Software"), to deal
     5  // in the Software without restriction, including without limitation the rights
     6  // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
     7  // copies of the Software, and to permit persons to whom the Software is
     8  // furnished to do so, subject to the following conditions:
     9  //
    10  // The above copyright notice and this permission notice shall be included in
    11  // all copies or substantial portions of the Software.
    12  //
    13  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    14  // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    15  // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    16  // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    17  // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    18  // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
    19  // THE SOFTWARE.
    20  
    21  package consolidators
    22  
    23  import (
    24  	"bytes"
    25  	"sort"
    26  
    27  	"github.com/m3db/m3/src/query/models"
    28  )
    29  
    30  type ascByID []multiResultSeries
    31  
    32  func (m ascByID) Len() int { return len(m) }
    33  func (m ascByID) Less(i, j int) bool {
    34  	return bytes.Compare(m[i].tags.LastComputedID(),
    35  		m[j].tags.LastComputedID()) == -1
    36  }
    37  func (m ascByID) Swap(i, j int) { m[i], m[j] = m[j], m[i] }
    38  
    39  type fetchResultMapWrapper struct {
    40  	resultMap *fetchResultMap
    41  }
    42  
    43  func (w *fetchResultMapWrapper) len() int {
    44  	return w.resultMap.Len()
    45  }
    46  
    47  func (w *fetchResultMapWrapper) list() []multiResultSeries {
    48  	result := make([]multiResultSeries, 0, w.len())
    49  	for _, results := range w.resultMap.Iter() {
    50  		result = append(result, results.value)
    51  	}
    52  
    53  	sort.Sort(ascByID(result))
    54  	return result
    55  }
    56  
    57  func (w *fetchResultMapWrapper) get(tags models.Tags) (multiResultSeries, bool) {
    58  	return w.resultMap.Get(tags)
    59  }
    60  
    61  func (w *fetchResultMapWrapper) close() {
    62  	w.resultMap.Reset()
    63  }
    64  
    65  func (w *fetchResultMapWrapper) set(
    66  	tags models.Tags, series multiResultSeries,
    67  ) {
    68  	series.tags = tags
    69  	w.resultMap.SetUnsafe(tags, series, fetchResultMapSetUnsafeOptions{
    70  		NoCopyKey:     true,
    71  		NoFinalizeKey: true,
    72  	})
    73  }
    74  
    75  // newFetchResultMapWrapper builds a wrapper on fetchResultMap functions.
    76  func newFetchResultMapWrapper(size int) *fetchResultMapWrapper {
    77  	return &fetchResultMapWrapper{
    78  		resultMap: _fetchResultMapAlloc(_fetchResultMapOptions{
    79  			hash: func(t models.Tags) fetchResultMapHash {
    80  				return fetchResultMapHash(t.LastComputedHashedID())
    81  			},
    82  			equals: func(x, y models.Tags) bool {
    83  				// NB: IDs are calculated once for tags, so any further calls to these
    84  				// equals is a simple lookup.
    85  				return bytes.Equal(x.LastComputedID(), y.LastComputedID())
    86  			},
    87  			initialSize: size,
    88  		}),
    89  	}
    90  }