| 215 | } |
| 216 | |
| 217 | void GBDT::Bagging(int iter) { |
| 218 | // if need bagging |
| 219 | |
| 220 | tree_learner_->SetBaggingData2(bag_data_indices_.data(), num_data_); |
| 221 | if ((bag_data_cnt_ < num_data_ && iter % config_->bagging_freq == 0) |
| 222 | || need_re_bagging_) { |
| 223 | need_re_bagging_ = false; |
| 224 | const data_size_t min_inner_size = 1000; |
| 225 | data_size_t inner_size = (num_data_ + num_threads_ - 1) / num_threads_; |
| 226 | if (inner_size < min_inner_size) { inner_size = min_inner_size; } |
| 227 | OMP_INIT_EX(); |
| 228 | #pragma omp parallel for schedule(static, 1) |
| 229 | for (int i = 0; i < num_threads_; ++i) { |
| 230 | OMP_LOOP_EX_BEGIN(); |
| 231 | left_cnts_buf_[i] = 0; |
| 232 | right_cnts_buf_[i] = 0; |
| 233 | data_size_t cur_start = i * inner_size; |
| 234 | if (cur_start > num_data_) { continue; } |
| 235 | data_size_t cur_cnt = inner_size; |
| 236 | if (cur_start + cur_cnt > num_data_) { cur_cnt = num_data_ - cur_start; } |
| 237 | Random cur_rand(config_->bagging_seed + iter * num_threads_ + i); |
| 238 | data_size_t cur_left_count = 0; |
| 239 | if (balanced_bagging_) { |
| 240 | cur_left_count = BalancedBaggingHelper(&cur_rand, cur_start, cur_cnt, tmp_indices_.data() + cur_start); |
| 241 | } else { |
| 242 | cur_left_count = BaggingHelper(&cur_rand, cur_start, cur_cnt, tmp_indices_.data() + cur_start); |
| 243 | } |
| 244 | offsets_buf_[i] = cur_start; |
| 245 | left_cnts_buf_[i] = cur_left_count; |
| 246 | right_cnts_buf_[i] = cur_cnt - cur_left_count; |
| 247 | OMP_LOOP_EX_END(); |
| 248 | } |
| 249 | OMP_THROW_EX(); |
| 250 | data_size_t left_cnt = 0; |
| 251 | left_write_pos_buf_[0] = 0; |
| 252 | right_write_pos_buf_[0] = 0; |
| 253 | for (int i = 1; i < num_threads_; ++i) { |
| 254 | left_write_pos_buf_[i] = left_write_pos_buf_[i - 1] + left_cnts_buf_[i - 1]; |
| 255 | right_write_pos_buf_[i] = right_write_pos_buf_[i - 1] + right_cnts_buf_[i - 1]; |
| 256 | } |
| 257 | left_cnt = left_write_pos_buf_[num_threads_ - 1] + left_cnts_buf_[num_threads_ - 1]; |
| 258 | |
| 259 | #pragma omp parallel for schedule(static, 1) |
| 260 | for (int i = 0; i < num_threads_; ++i) { |
| 261 | OMP_LOOP_EX_BEGIN(); |
| 262 | if (left_cnts_buf_[i] > 0) { |
| 263 | std::memcpy(bag_data_indices_.data() + left_write_pos_buf_[i], |
| 264 | tmp_indices_.data() + offsets_buf_[i], left_cnts_buf_[i] * sizeof(data_size_t)); |
| 265 | } |
| 266 | if (right_cnts_buf_[i] > 0) { |
| 267 | std::memcpy(bag_data_indices_.data() + left_cnt + right_write_pos_buf_[i], |
| 268 | tmp_indices_.data() + offsets_buf_[i] + left_cnts_buf_[i], right_cnts_buf_[i] * sizeof(data_size_t)); |
| 269 | } |
| 270 | OMP_LOOP_EX_END(); |
| 271 | } |
| 272 | OMP_THROW_EX(); |
| 273 | bag_data_cnt_ = left_cnt; |
| 274 | Log::Debug("Re-bagging, using %d data to train", bag_data_cnt_); |
nothing calls this directly
no test coverage detected