github.com/balzaczyy/golucene@v0.0.0-20151210033525-d0be9ee89713/core/index/fields.go (about)

     1  package index
     2  
     3  import (
     4  	. "github.com/balzaczyy/golucene/core/index/model"
     5  )
     6  
     7  type MultiFields struct {
     8  	subs      []Fields
     9  	subSlices []ReaderSlice
    10  	termsMap  map[string]Terms // synchronized
    11  }
    12  
    13  func NewMultiFields(subs []Fields, subSlices []ReaderSlice) MultiFields {
    14  	return MultiFields{subs, subSlices, make(map[string]Terms)}
    15  }
    16  
    17  func (mf MultiFields) Terms(field string) Terms {
    18  	if ans, ok := mf.termsMap[field]; ok {
    19  		return ans
    20  	}
    21  
    22  	// Lazy init: first time this field is requested, we
    23  	// create & add to terms:
    24  	subs2 := make([]Terms, 0)
    25  	slices2 := make([]ReaderSlice, 0)
    26  
    27  	// Gather all sub-readers that share this field
    28  	for i, v := range mf.subs {
    29  		terms := v.Terms(field)
    30  		if terms.Iterator != nil {
    31  			subs2 = append(subs2, terms)
    32  			slices2 = append(slices2, mf.subSlices[i])
    33  		}
    34  	}
    35  	if len(subs2) == 0 {
    36  		return nil
    37  		// don't cache this case with an unbounded cache, since the number of fields that don't exist
    38  		// is unbounded.
    39  	}
    40  	ans := NewMultiTerms(subs2, slices2)
    41  	mf.termsMap[field] = ans
    42  	return ans
    43  }
    44  
    45  func GetMultiFields(r IndexReader) Fields {
    46  	// log.Print("Obtaining MultiFields from ", r)
    47  	leaves := r.Leaves()
    48  	switch len(leaves) {
    49  	case 0:
    50  		// log.Print("No fields are found.")
    51  		// no fields
    52  		return nil
    53  	case 1:
    54  		// already an atomic reader / reader with one leave
    55  		return leaves[0].Reader().(AtomicReader).Fields()
    56  	default:
    57  		fields := make([]Fields, 0)
    58  		slices := make([]ReaderSlice, 0)
    59  		for _, ctx := range leaves {
    60  			f := ctx.Reader().(AtomicReader).Fields()
    61  			if f == nil {
    62  				continue
    63  			}
    64  			fields = append(fields, f)
    65  			slices = append(slices, ReaderSlice{ctx.DocBase, r.MaxDoc(), len(fields)})
    66  		}
    67  		// log.Printf("Found %v fields in %v slices.", len(fields), len(slices))
    68  		switch len(fields) {
    69  		case 0:
    70  			return nil
    71  		case 1:
    72  			return fields[0]
    73  		default:
    74  			return NewMultiFields(fields, slices)
    75  		}
    76  	}
    77  }
    78  
    79  func GetMultiTerms(r IndexReader, field string) Terms {
    80  	// log.Printf("Loading field '%v' from %v", field, r)
    81  	fields := GetMultiFields(r)
    82  	if fields.Terms == nil {
    83  		return nil
    84  	}
    85  	return fields.Terms(field)
    86  }