21 boost::get(boost::vertex_bundle, this->
main_graph);
23 boost::get(boost::edge_bundle, this->
main_graph);
26 std::pair<T, T> pair_energy;
30 for (uint32_t ind_ver = 0; ind_ver < this->
nVertex; ind_ver++) {
33 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
34 energy += .5 * vertex_attribute_map(i_ver).weight *
35 pow(vertex_attribute_map(i_ver).observation[i_dim] -
36 vertex_attribute_map(i_ver).value[i_dim],
40 pair_energy.first = energy;
43 i_edg_end = boost::edges(this->
main_graph).second;
44 for (i_edg = boost::edges(this->
main_graph).first; i_edg != i_edg_end;
46 if (!edge_attribute_map(*i_edg).realEdge) {
49 energy += .5 * edge_attribute_map(*i_edg).isActive *
50 this->parameter.reg_strenth *
51 edge_attribute_map(*i_edg).weight;
53 pair_energy.second = energy;
70 uint32_t nb_comp =
static_cast<uint32_t
>(this->
components.size());
72 boost::get(boost::vertex_bundle, this->
main_graph);
76 std::vector<bool> binary_label(this->
nVertex);
85 for (uint32_t i_step = 1; i_step <= this->
parameter.flow_steps;
94 boost::boykov_kolmogorov_max_flow(
103 for (uint32_t ind_com = 0; ind_com < nb_comp; ind_com++) {
107 for (uint32_t i_ver = 0;
108 i_ver < this->
components[ind_com].size(); i_ver++) {
109 binary_label[vertex_index_map(
111 (vertex_attribute_map(
114 vertex_attribute_map(this->
sink).color);
133 boost::get(boost::vertex_bundle, this->
main_graph);
136 uint32_t nb_comp =
static_cast<uint32_t
>(this->
components.size());
141 #pragma omp parallel for if (nb_comp >= omp_get_num_threads()) schedule(dynamic)
143 for (uint32_t ind_com = 0; ind_com < nb_comp; ind_com++) {
144 std::vector<std::vector<T>> kernels(2, std::vector<T>(this->
dim));
149 static_cast<uint32_t
>(this->
components[ind_com].size());
150 std::vector<bool> potential_label(comp_size);
151 std::vector<T> energy_array(comp_size);
156 for (uint32_t init_kmeans = 0;
157 init_kmeans < this->
parameter.kmeans_resampling;
161 uint32_t first_kernel = std::rand() % comp_size,
163 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
165 vertex_attribute_map(
172 #pragma omp parallel for if (nb_comp < omp_get_num_threads()) \
173 shared(best_energy) schedule(static)
175 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
176 energy_array[i_ver] = 0;
177 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
178 energy_array[i_ver] +=
179 pow(vertex_attribute_map(
181 .observation[i_dim] -
184 vertex_attribute_map(
188 best_energy += energy_array[i_ver];
193 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
194 current_energy -= energy_array[i_ver];
197 second_kernel = i_ver;
201 for (uint32_t i_dim = 0; i_dim < this->
dim;
204 vertex_attribute_map(
209 for (uint32_t ite_kmeans = 0;
210 ite_kmeans < this->
parameter.kmeans_ite; ite_kmeans++) {
214 #pragma omp parallel for if (nb_comp < omp_get_num_threads()) \
215 shared(potential_label) schedule(static)
217 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
218 std::vector<T> distance_kernels(2);
219 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
220 distance_kernels[0] += pow(
221 vertex_attribute_map(
223 .observation[i_dim] -
226 distance_kernels[1] += pow(
227 vertex_attribute_map(
229 .observation[i_dim] -
233 potential_label[i_ver] =
234 distance_kernels[0] > distance_kernels[1];
238 total_weight[0] = 0.;
239 total_weight[1] = 0.;
240 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
241 kernels[0][i_dim] = 0;
242 kernels[1][i_dim] = 0;
245 #pragma omp parallel for if (nb_comp < omp_get_num_threads()) \
246 shared(potential_label) schedule(static)
248 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
249 if (vertex_attribute_map(
254 if (potential_label[i_ver]) {
256 vertex_attribute_map(
259 for (uint32_t i_dim = 0; i_dim < this->
dim;
262 vertex_attribute_map(
265 .observation[i_dim] *
266 vertex_attribute_map(
273 vertex_attribute_map(
276 for (uint32_t i_dim = 0; i_dim < this->
dim;
279 vertex_attribute_map(
282 .observation[i_dim] *
283 vertex_attribute_map(
290 if ((total_weight[0] == 0) || (total_weight[1] == 0)) {
295 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
296 kernels[0][i_dim] = kernels[0][i_dim] / total_weight[0];
297 kernels[1][i_dim] = kernels[1][i_dim] / total_weight[1];
303 #pragma omp parallel for if (nb_comp < omp_get_num_threads()) \
304 shared(potential_label) schedule(static)
306 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
307 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
308 if (potential_label[i_ver]) {
310 pow(vertex_attribute_map(
313 .observation[i_dim] -
316 vertex_attribute_map(
321 pow(vertex_attribute_map(
324 .observation[i_dim] -
327 vertex_attribute_map(
333 if (current_energy < best_energy) {
334 best_energy = current_energy;
335 for (uint32_t i_ver = 0; i_ver < comp_size; i_ver++) {
336 binary_label[vertex_index_map(
338 potential_label[i_ver];
350 const uint32_t& nb_comp,
351 const std::vector<bool>& binary_label) {
354 #pragma omp parallel for if (nb_comp >= omp_get_num_threads()) schedule(dynamic)
356 for (uint32_t ind_com = 0; ind_com < nb_comp; ind_com++) {
369 const uint32_t& ind_com,
370 const std::vector<bool>& binary_label) {
374 boost::get(boost::vertex_bundle, this->
main_graph);
378 total_weight[0] = 0.;
379 total_weight[1] = 0.;
381 for (uint32_t i_ver = 0; i_ver < this->
components[ind_com].size();
383 if (vertex_attribute_map(this->
components[ind_com][i_ver]).weight ==
387 if (binary_label[vertex_index_map(
390 vertex_attribute_map(this->
components[ind_com][i_ver])
392 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
394 vertex_attribute_map(
396 .observation[i_dim] *
397 vertex_attribute_map(
403 vertex_attribute_map(this->
components[ind_com][i_ver])
405 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
407 vertex_attribute_map(
409 .observation[i_dim] *
410 vertex_attribute_map(
416 if ((total_weight[0] == 0) || (total_weight[1] == 0)) {
419 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
421 vertex_attribute_map(this->
components[ind_com][0])
424 vertex_attribute_map(this->
components[ind_com][0])
428 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
429 center[0][i_dim] = center[0][i_dim] / total_weight[0];
430 center[1][i_dim] = center[1][i_dim] / total_weight[1];
441 boost::get(boost::vertex_bundle, this->
main_graph);
443 boost::get(boost::edge_bundle, this->
main_graph);
447 uint32_t nb_comp =
static_cast<uint32_t
>(this->
components.size());
449 #pragma omp parallel for if (nb_comp >= omp_get_num_threads()) schedule(dynamic)
451 for (uint32_t ind_com = 0; ind_com < nb_comp; ind_com++) {
459 for (uint32_t i_ver = 0; i_ver < this->
components[ind_com].size();
468 edge_attribute_map(desc_v2source)
474 if (vertex_attribute_map(desc_v).weight ==
476 edge_attribute_map(desc_source2v).capacity = 0;
477 edge_attribute_map(desc_v2sink).capacity = 0;
480 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
481 cost_B += 0.5 * vertex_attribute_map(desc_v).weight *
482 (pow(centers.
centroids[ind_com][0][i_dim], 2) -
483 2 * (centers.
centroids[ind_com][0][i_dim] *
484 vertex_attribute_map(desc_v)
485 .observation[i_dim]));
486 cost_notB += 0.5 * vertex_attribute_map(desc_v).weight *
487 (pow(centers.
centroids[ind_com][1][i_dim], 2) -
488 2 * (centers.
centroids[ind_com][1][i_dim] *
489 vertex_attribute_map(desc_v)
490 .observation[i_dim]));
492 if (cost_B > cost_notB) {
493 edge_attribute_map(desc_source2v).capacity =
495 edge_attribute_map(desc_v2sink).capacity = 0.;
497 edge_attribute_map(desc_source2v).capacity = 0.;
498 edge_attribute_map(desc_v2sink).capacity =
506 for (boost::tie(i_edg, i_edg_end) = boost::edges(this->
main_graph);
507 i_edg != i_edg_end; ++i_edg) {
508 if (!edge_attribute_map(*i_edg).realEdge) {
511 if (!edge_attribute_map(*i_edg).isActive) {
512 edge_attribute_map(*i_edg).capacity =
513 edge_attribute_map(*i_edg).weight *
514 this->parameter.reg_strenth;
516 edge_attribute_map(*i_edg).capacity = 0;
526 const uint32_t& ind_com)
override {
528 boost::get(boost::vertex_bundle, this->
main_graph);
530 std::vector<T> compValue(this->
dim);
531 std::fill((compValue.begin()), (compValue.end()), 0);
533 #pragma omp parallel for if (this->parameter.parallel) schedule(static)
535 for (uint32_t ind_ver = 0; ind_ver < this->
components[ind_com].size();
538 vertex_attribute_map(this->
components[ind_com][ind_ver])
540 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
542 vertex_attribute_map(this->
components[ind_com][ind_ver])
543 .observation[i_dim] *
544 vertex_attribute_map(this->
components[ind_com][ind_ver])
547 vertex_attribute_map(this->
components[ind_com][ind_ver])
548 .in_component = ind_com;
550 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
551 compValue[i_dim] = compValue[i_dim] / total_weight;
553 for (uint32_t ind_ver = 0; ind_ver < this->
components[ind_com].size();
555 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
556 vertex_attribute_map(this->
components[ind_com][ind_ver])
557 .value[i_dim] = compValue[i_dim];
560 return std::pair<std::vector<T>, T>(compValue, total_weight);
572 std::vector<T> merge_value(this->
dim);
575 for (uint32_t i_dim = 0; i_dim < this->
dim; i_dim++) {
577 (reduced_vertex_attribute_map(comp1).weight *
578 reduced_vertex_attribute_map(comp1).value[i_dim] +
579 reduced_vertex_attribute_map(comp2).weight *
580 reduced_vertex_attribute_map(comp2).value[i_dim]) /
581 (reduced_vertex_attribute_map(comp1).weight +
582 reduced_vertex_attribute_map(comp2).weight);
584 (pow(merge_value[i_dim], 2) *
585 (reduced_vertex_attribute_map(comp1).weight +
586 reduced_vertex_attribute_map(comp2).weight) -
587 pow(reduced_vertex_attribute_map(comp1).value[i_dim], 2) *
588 reduced_vertex_attribute_map(comp1).weight -
589 pow(reduced_vertex_attribute_map(comp2).value[i_dim], 2) *
590 reduced_vertex_attribute_map(comp2).weight);
592 return std::pair<std::vector<T>, T>(merge_value, gain);
std::vector< std::vector< std::vector< T > > > centroids
boost::vec_adj_list_vertex_property_map< Graph< T >, Graph< T > *, VertexAttribute< T >, VertexAttribute< T > &, boost::vertex_bundle_t > VertexAttributeMap
typename boost::graph_traits< Graph< T > >::edge_iterator EdgeIterator
boost::graph_traits< boost::adjacency_list< boost::vecS, boost::vecS, boost::directedS > >::edge_descriptor EdgeDescriptor
typename boost::graph_traits< CP::Graph< T > >::vertex_descriptor VertexDescriptor
typename boost::property_map< Graph< T >, boost::vertex_index_t >::type VertexIndexMap
boost::adj_list_edge_property_map< boost::directed_tag, EdgeAttribute< T >, EdgeAttribute< T > &, uint64_t, CP::EdgeAttribute< T >, boost::edge_bundle_t > EdgeAttributeMap
Matrix< T > random_sample(Matrix< T > &srcMatrix, size_t size, bool remove=false)
void compute_center(std::vector< std::vector< T >> ¢er, const uint32_t &ind_com, const std::vector< bool > &binary_label)
void compute_centers(VectorOfCentroids< T > ¢ers, const uint32_t &nb_comp, const std::vector< bool > &binary_label)
void init_labels(std::vector< bool > &binary_label)
std::pair< std::vector< T >, T > compute_value(const uint32_t &ind_com) override
void set_capacities(const VectorOfCentroids< T > ¢ers)
std::pair< std::vector< T >, T > compute_merge_gain(const VertexDescriptor< T > &comp1, const VertexDescriptor< T > &comp2) override
std::pair< T, T > compute_energy() override
CPparameter< T > parameter
std::vector< std::vector< VertexDescriptor< T > > > components
VertexDescriptor< T > sink
VertexDescriptor< T > source
size_t activate_edges(bool allows_saturation=true)
std::vector< bool > saturated_components
void saturateComponent(const uint32_t &ind_com)