diff --git a/matchtree.go b/matchtree.go index 906b2b86..9e2a8406 100644 --- a/matchtree.go +++ b/matchtree.go @@ -29,8 +29,10 @@ import ( // A docIterator iterates over documents in order. type docIterator interface { - // provide the next document where we can may find something - // interesting. + // provide the next document where we may find something interesting. + // + // This is like a "peek" and shouldn't mutate state. prepare is what should + // change state. nextDoc() uint32 // clears any per-document state of the docIterator, and @@ -39,6 +41,8 @@ type docIterator interface { prepare(nextDoc uint32) } +// costs are passed in increasing order to matchTree.matches until they do not +// return matchesRequiresHigherCost. const ( costConst = 0 costMemory = 1 @@ -51,14 +55,25 @@ const ( costMax = costRegexp ) +// matchesState is an enum for the possible state a call to matchTree.matches. type matchesState uint8 const ( + // matchesRequiresHigherCost is returned when matchTree.matches hasn't done + // a search yet since the cost value is not high enough. matchesRequiresHigherCost matchesState = iota + + // matchesFound is returned when matchTree.matches has done a search and + // found one or more matches. matchesFound + + // matchesNone is returned when matchTree.matches has done a search and + // found nothing. matchesNone ) +// matchesStatePred is a helper which returns matchesFound if b is true +// otherwise returns matchesNone. func matchesStatePred(b bool) matchesState { if b { return matchesFound @@ -66,6 +81,8 @@ func matchesStatePred(b bool) matchesState { return matchesNone } +// matchesStateForSlice is a helper which returns matchesFound if v is +// non-empty otherwise returns matchesNone. func matchesStateForSlice[T any](v []T) matchesState { return matchesStatePred(len(v) > 0) } @@ -94,12 +111,14 @@ func matchesStateForSlice[T any](v []T) matchesState { // // - evaluate the tree using matches(), storing the result in map. // -// - if the complete tree returns (matches() == true) for the document, -// collect all text matches by looking at leaf matchTrees +// - if the complete tree returns (matches() != matchesRequiresHigherCost) +// for the document, collect all text matches by looking at leaf +// matchTrees. type matchTree interface { docIterator - // returns whether this matches, and if we are sure. + // matches if cost is high enough, caching known values for future + // evaluation at higher costs. See documentation for matchesState's values. matches(cp *contentProvider, cost int, known map[matchTree]bool) matchesState }