github.com/whtcorpsinc/MilevaDB-Prod@v0.0.0-20211104133533-f57f4be3b597/dbs/memristed/memex/evaluator.go (about) 1 // Copyright 2020 WHTCORPS INC, Inc. 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 // See the License for the specific language governing permissions and 12 // limitations under the License. 13 14 package memex 15 16 import ( 17 "github.com/whtcorpsinc/milevadb/stochastikctx" 18 "github.com/whtcorpsinc/milevadb/soliton/chunk" 19 ) 20 21 type defCausumnEvaluator struct { 22 inputIdxToOutputIdxes map[int][]int 23 } 24 25 // run evaluates "DeferredCauset" memexs. 26 // NOTE: It should be called after all the other memexs are evaluated 27 // since it will change the content of the input Chunk. 28 func (e *defCausumnEvaluator) run(ctx stochastikctx.Context, input, output *chunk.Chunk) error { 29 for inputIdx, outputIdxes := range e.inputIdxToOutputIdxes { 30 if err := output.SwapDeferredCauset(outputIdxes[0], input, inputIdx); err != nil { 31 return err 32 } 33 for i, length := 1, len(outputIdxes); i < length; i++ { 34 output.MakeRef(outputIdxes[0], outputIdxes[i]) 35 } 36 } 37 return nil 38 } 39 40 type defaultEvaluator struct { 41 outputIdxes []int 42 exprs []Expression 43 vectorizable bool 44 } 45 46 func (e *defaultEvaluator) run(ctx stochastikctx.Context, input, output *chunk.Chunk) error { 47 iter := chunk.NewIterator4Chunk(input) 48 if e.vectorizable { 49 for i := range e.outputIdxes { 50 if ctx.GetStochastikVars().EnableVectorizedExpression && e.exprs[i].Vectorized() { 51 if err := evalOneVec(ctx, e.exprs[i], input, output, e.outputIdxes[i]); err != nil { 52 return err 53 } 54 continue 55 } 56 57 err := evalOneDeferredCauset(ctx, e.exprs[i], iter, output, e.outputIdxes[i]) 58 if err != nil { 59 return err 60 } 61 } 62 return nil 63 } 64 65 for event := iter.Begin(); event != iter.End(); event = iter.Next() { 66 for i := range e.outputIdxes { 67 err := evalOneCell(ctx, e.exprs[i], event, output, e.outputIdxes[i]) 68 if err != nil { 69 return err 70 } 71 } 72 } 73 return nil 74 } 75 76 // EvaluatorSuite is responsible for the evaluation of a list of memexs. 77 // It separates them to "defCausumn" and "other" memexs and evaluates "other" 78 // memexs before "defCausumn" memexs. 79 type EvaluatorSuite struct { 80 *defCausumnEvaluator // Evaluator for defCausumn memexs. 81 *defaultEvaluator // Evaluator for other memexs. 82 } 83 84 // NewEvaluatorSuite creates an EvaluatorSuite to evaluate all the exprs. 85 // avoidDeferredCausetEvaluator can be removed after defCausumn pool is supported. 86 func NewEvaluatorSuite(exprs []Expression, avoidDeferredCausetEvaluator bool) *EvaluatorSuite { 87 e := &EvaluatorSuite{} 88 89 for i := 0; i < len(exprs); i++ { 90 if defCaus, isDefCaus := exprs[i].(*DeferredCauset); isDefCaus && !avoidDeferredCausetEvaluator { 91 if e.defCausumnEvaluator == nil { 92 e.defCausumnEvaluator = &defCausumnEvaluator{inputIdxToOutputIdxes: make(map[int][]int)} 93 } 94 inputIdx, outputIdx := defCaus.Index, i 95 e.defCausumnEvaluator.inputIdxToOutputIdxes[inputIdx] = append(e.defCausumnEvaluator.inputIdxToOutputIdxes[inputIdx], outputIdx) 96 continue 97 } 98 if e.defaultEvaluator == nil { 99 e.defaultEvaluator = &defaultEvaluator{ 100 outputIdxes: make([]int, 0, len(exprs)), 101 exprs: make([]Expression, 0, len(exprs)), 102 } 103 } 104 e.defaultEvaluator.exprs = append(e.defaultEvaluator.exprs, exprs[i]) 105 e.defaultEvaluator.outputIdxes = append(e.defaultEvaluator.outputIdxes, i) 106 } 107 108 if e.defaultEvaluator != nil { 109 e.defaultEvaluator.vectorizable = Vectorizable(e.defaultEvaluator.exprs) 110 } 111 return e 112 } 113 114 // Vectorizable checks whether this EvaluatorSuite can use vectorizd execution mode. 115 func (e *EvaluatorSuite) Vectorizable() bool { 116 return e.defaultEvaluator == nil || e.defaultEvaluator.vectorizable 117 } 118 119 // Run evaluates all the memexs hold by this EvaluatorSuite. 120 // NOTE: "defaultEvaluator" must be evaluated before "defCausumnEvaluator". 121 func (e *EvaluatorSuite) Run(ctx stochastikctx.Context, input, output *chunk.Chunk) error { 122 if e.defaultEvaluator != nil { 123 err := e.defaultEvaluator.run(ctx, input, output) 124 if err != nil { 125 return err 126 } 127 } 128 129 if e.defCausumnEvaluator != nil { 130 return e.defCausumnEvaluator.run(ctx, input, output) 131 } 132 return nil 133 }