3 #ifndef GRAIL_ROULETTE_SAMPLER_H
4 #define GRAIL_ROULETTE_SAMPLER_H
34 RouletteSampler(
const std::vector<std::unique_ptr<T>>& fitnessHavingElements);
40 void Initialize(
const std::vector<std::unique_ptr<T>>& fitnessHavingElements);
47 T*
Sample(std::mt19937_64& randGen);
62 std::vector<T*>
SampleMany(
size_t count, std::mt19937_64& randGen);
86 std::size_t SampleIndex(std::mt19937_64& randGen);
92 std::size_t SampleIndexWithReturn(std::mt19937_64& randGen)
const;
94 std::size_t RemoveIndex(std::size_t index);
96 std::vector<T*> data{};
97 double totalFitness = 0.0;
103 totalFitness -= data[index]->GetFitness();
104 data.erase(data.begin() + index);
113 for(
auto& individual : fitnessHavingElements)
115 totalFitness += individual->GetFitness();
116 data.push_back(individual.get());
129 Initialize(fitnessHavingElements);
135 return RemoveIndex(SampleIndexWithReturn(randGen));
139 inline std::size_t RouletteSampler<T>::SampleIndexWithReturn(std::mt19937_64& randGen)
const
141 if(totalFitness <= std::numeric_limits<double>::epsilon())
143 return std::uniform_int_distribution<size_t>(0, data.size())(randGen);
146 double val = std::uniform_real_distribution<double>(0, totalFitness)(randGen);
147 for(
size_t i = 0; i < data.size(); ++i)
149 if(val < data[i]->GetFitness())
154 val -= data[i]->GetFitness();
156 return data.size() - 1;
162 std::vector<size_t> retData;
163 if(count >= data.size())
165 retData.resize(data.size());
166 std::iota(retData.begin(), retData.end(), 0);
170 for(
size_t i = 0; i < count; ++i)
172 retData.push_back(SampleIndex(randGen));
186 std::size_t index = SampleIndexWithReturn(randGen);
187 T* individual = data[index];
195 if (data.size() == 0)
200 return data[SampleIndexWithReturn(randGen)];
206 if(count >= data.size())
208 return std::vector<T*>(data);
211 std::vector<T*> retData;
212 for(std::size_t i = 0; i < count; ++i)
214 retData.push_back(Sample(randGen));
222 if (count >= data.size())
224 return std::vector<T*>(data);
227 std::vector<T*> retData;
228 for (std::size_t i = 0; i < count; ++i)
230 retData.push_back(SampleWithReturn(randGen));
237 #endif // GRAIL_ROULETTE_SAMPLER_H