| 136 | } |
| 137 | |
| 138 | void TStaticCtrProvider::SetupBinFeatureIndexes(const TConstArrayRef<TFloatFeature> floatFeatures, |
| 139 | const TConstArrayRef<TOneHotFeature> oheFeatures, |
| 140 | const TConstArrayRef<TCatFeature> catFeatures) { |
| 141 | ui32 currentIndex = 0; |
| 142 | FloatFeatureIndexes.clear(); |
| 143 | for (const auto& floatFeature : floatFeatures) { |
| 144 | if (!floatFeature.UsedInModel()) { |
| 145 | continue; |
| 146 | } |
| 147 | for (size_t borderIdx = 0; borderIdx < floatFeature.Borders.size(); ++borderIdx) { |
| 148 | TBinFeatureIndexValue featureIdx{currentIndex + (ui32)borderIdx / MAX_VALUES_PER_BIN, false, (ui8)((borderIdx % MAX_VALUES_PER_BIN)+ 1)}; |
| 149 | TFloatSplit split{floatFeature.Position.Index, floatFeature.Borders[borderIdx]}; |
| 150 | FloatFeatureIndexes[split] = featureIdx; |
| 151 | } |
| 152 | currentIndex += (floatFeature.Borders.size() + MAX_VALUES_PER_BIN - 1) / MAX_VALUES_PER_BIN; |
| 153 | } |
| 154 | OneHotFeatureIndexes.clear(); |
| 155 | for (const auto& oheFeature : oheFeatures) { |
| 156 | for (size_t valueId = 0; valueId < oheFeature.Values.size(); ++valueId) { |
| 157 | TBinFeatureIndexValue featureIdx{currentIndex + (ui32)valueId / MAX_VALUES_PER_BIN, true, (ui8)((valueId % MAX_VALUES_PER_BIN) + 1)}; |
| 158 | TOneHotSplit feature{oheFeature.CatFeatureIndex, oheFeature.Values[valueId]}; |
| 159 | OneHotFeatureIndexes[feature] = featureIdx; |
| 160 | } |
| 161 | currentIndex += (oheFeature.Values.size() + MAX_VALUES_PER_BIN - 1) / MAX_VALUES_PER_BIN; |
| 162 | } |
| 163 | CatFeatureIndex.clear(); |
| 164 | for (const auto& catFeature : catFeatures) { |
| 165 | if (catFeature.UsedInModel()) { |
| 166 | const int prevSize = CatFeatureIndex.ysize(); |
| 167 | CatFeatureIndex[catFeature.Position.Index] = prevSize; |
| 168 | } |
| 169 | } |
| 170 | } |
| 171 | |
| 172 | TIntrusivePtr<ICtrProvider> TStaticCtrProvider::Clone() const { |
| 173 | TIntrusivePtr<TStaticCtrProvider> result = new TStaticCtrProvider(); |
no test coverage detected