Euclidian distance fixed, C random now
This commit is contained in:
		
							parent
							
								
									e1a7b127af
								
							
						
					
					
						commit
						b2361e1974
					
				@ -3,13 +3,10 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
#include <opencv2/core/core.hpp>
 | 
					#include <opencv2/core/core.hpp>
 | 
				
			||||||
#include <opencv2/highgui/highgui.hpp>
 | 
					#include <opencv2/highgui/highgui.hpp>
 | 
				
			||||||
#include <random>
 | 
					 | 
				
			||||||
#include <spdlog/spdlog.h>
 | 
					#include <spdlog/spdlog.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void method1(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations,
 | 
					void method1(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations);
 | 
				
			||||||
             std::mt19937 &t_gen);
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
void method2(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations,
 | 
					void method2(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations);
 | 
				
			||||||
             std::mt19937 &t_gen);
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif /* GENETIC_IMAGE_INCLUDE_GENIMG_METHODS_HH_ */
 | 
					#endif /* GENETIC_IMAGE_INCLUDE_GENIMG_METHODS_HH_ */
 | 
				
			||||||
 | 
				
			|||||||
@ -19,11 +19,10 @@ std::pair<cv::Mat, cv::Mat> init_image(std::string const &t_input_file) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
double euclidian_distance(cv::Mat const &t_img1, cv::Mat const &t_img2) {
 | 
					double euclidian_distance(cv::Mat const &t_img1, cv::Mat const &t_img2) {
 | 
				
			||||||
  double euclidian = 0.0;
 | 
					  double euclidian = 0.0;
 | 
				
			||||||
  for (int w = 0; w < t_img1.size().width; ++w) {
 | 
					  for (auto itr1 = t_img1.begin<uchar>(), itr2 = t_img2.begin<uchar>();
 | 
				
			||||||
    for (int h = 0; h < t_img1.size().height; ++h) {
 | 
					       itr1 != t_img1.end<uchar>() && itr2 != t_img2.end<uchar>();
 | 
				
			||||||
      euclidian += std::abs(std::pow(t_img1.at<uchar>(h, w), 2) -
 | 
					       ++itr1, ++itr2) {
 | 
				
			||||||
                            std::pow(t_img2.at<uchar>(h, w), 2));
 | 
					    euclidian += std::pow(*itr1 - *itr2, 2);
 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  euclidian = std::sqrt(euclidian);
 | 
					  euclidian = std::sqrt(euclidian);
 | 
				
			||||||
  return euclidian;
 | 
					  return euclidian;
 | 
				
			||||||
 | 
				
			|||||||
@ -5,12 +5,15 @@
 | 
				
			|||||||
#include <spdlog/spdlog.h>
 | 
					#include <spdlog/spdlog.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void drawSquare(cv::Mat &t_img, cv::Point const &t_top_left, int const t_size,
 | 
					void drawSquare(cv::Mat &t_img, cv::Point const &t_top_left, int const t_size,
 | 
				
			||||||
                 cv::Scalar const &t_color) {
 | 
					                cv::Scalar const &t_color) {
 | 
				
			||||||
  std::unique_ptr<cv::Point> points(new cv::Point[4]);
 | 
					  auto points = std::make_unique<cv::Point[]>(4);
 | 
				
			||||||
  points.get()[0] = t_top_left;
 | 
					  points.get()[0] = t_top_left;
 | 
				
			||||||
  points.get()[1] = cv::Point{t_top_left.x, t_top_left.y + t_size};
 | 
					  points.get()[1] = cv::Point{t_top_left.x,          t_top_left.y + t_size};
 | 
				
			||||||
  points.get()[2] = cv::Point{t_top_left.x + t_size, t_top_left.y + t_size};
 | 
					  points.get()[2] = cv::Point{t_top_left.x + t_size, t_top_left.y + t_size};
 | 
				
			||||||
  points.get()[3] = cv::Point{t_top_left.x + t_size, t_top_left.y};
 | 
					  points.get()[3] = cv::Point{t_top_left.x + t_size, t_top_left.y};
 | 
				
			||||||
 | 
					  // spdlog::debug("Size:{} 1[{},{}] 2[{},{}] 3[{},{}] 4[{},{}]", t_size,
 | 
				
			||||||
 | 
					  //               points[0].x, points[0].y, points[1].x, points[1].y, points[2].x,
 | 
				
			||||||
 | 
					  //               points[2].y, points[3].x, points[3].y);
 | 
				
			||||||
  fillConvexPoly(t_img, points.get(), 4, t_color);
 | 
					  fillConvexPoly(t_img, points.get(), 4, t_color);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										12
									
								
								src/main.cc
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								src/main.cc
									
									
									
									
									
								
							@ -2,8 +2,11 @@
 | 
				
			|||||||
#include "methods.hh"
 | 
					#include "methods.hh"
 | 
				
			||||||
#include "parseargs.hh"
 | 
					#include "parseargs.hh"
 | 
				
			||||||
#include <iostream>
 | 
					#include <iostream>
 | 
				
			||||||
 | 
					#include <cstdlib>
 | 
				
			||||||
 | 
					#include <ctime>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
int main(int ac, char **av) {
 | 
					int main(int ac, char **av) {
 | 
				
			||||||
 | 
					  std::srand(std::time(nullptr));
 | 
				
			||||||
  auto const [input_file, output_file, iterations, method,
 | 
					  auto const [input_file, output_file, iterations, method,
 | 
				
			||||||
              verbose] = parse_args(ac, av);
 | 
					              verbose] = parse_args(ac, av);
 | 
				
			||||||
  spdlog::set_level(verbose ? spdlog::level::debug : spdlog::level::info);
 | 
					  spdlog::set_level(verbose ? spdlog::level::debug : spdlog::level::info);
 | 
				
			||||||
@ -11,16 +14,14 @@ int main(int ac, char **av) {
 | 
				
			|||||||
  spdlog::debug("Output file:\t{}", output_file.native());
 | 
					  spdlog::debug("Output file:\t{}", output_file.native());
 | 
				
			||||||
  spdlog::debug("Iterations:\t{}", iterations);
 | 
					  spdlog::debug("Iterations:\t{}", iterations);
 | 
				
			||||||
  auto [input_image, process_image] = init_image(input_file.native());
 | 
					  auto [input_image, process_image] = init_image(input_file.native());
 | 
				
			||||||
  std::random_device rd;
 | 
					 | 
				
			||||||
  std::mt19937 gen(rd());
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  switch (method) {
 | 
					  switch (method) {
 | 
				
			||||||
  case 1: {
 | 
					  case 1: {
 | 
				
			||||||
    method1(input_image, process_image, iterations, gen);
 | 
					    method1(input_image, process_image, iterations);
 | 
				
			||||||
    break;
 | 
					    break;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  case 2: {
 | 
					  case 2: {
 | 
				
			||||||
    method2(input_image, process_image, iterations, gen);
 | 
					    method2(input_image, process_image, iterations);
 | 
				
			||||||
    break;
 | 
					    break;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  default:
 | 
					  default:
 | 
				
			||||||
@ -29,8 +30,5 @@ int main(int ac, char **av) {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  cv::imwrite(output_file.native(), process_image);
 | 
					  cv::imwrite(output_file.native(), process_image);
 | 
				
			||||||
 | 
					 | 
				
			||||||
  // Launch image generation
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  return 0;
 | 
					  return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -3,6 +3,7 @@
 | 
				
			|||||||
#include "drawing.hh"
 | 
					#include "drawing.hh"
 | 
				
			||||||
#include <algorithm>
 | 
					#include <algorithm>
 | 
				
			||||||
#include <array>
 | 
					#include <array>
 | 
				
			||||||
 | 
					#include <cstdlib>
 | 
				
			||||||
#include <thread>
 | 
					#include <thread>
 | 
				
			||||||
#include <vector>
 | 
					#include <vector>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -12,20 +13,31 @@ std::mutex numbers_mutex;
 | 
				
			|||||||
using randint = std::uniform_int_distribution<>;
 | 
					using randint = std::uniform_int_distribution<>;
 | 
				
			||||||
using Color = std::array<uchar, 3>;
 | 
					using Color = std::array<uchar, 3>;
 | 
				
			||||||
using ColorSet = std::vector<Color>;
 | 
					using ColorSet = std::vector<Color>;
 | 
				
			||||||
 | 
					using std::rand;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
namespace methods_private {
 | 
					namespace methods_private {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
cv::Scalar randomColor(std::mt19937 &t_gen) {
 | 
					void adjustSize(cv::Mat const &t_process_img, cv::Point &t_top_left, int size) {
 | 
				
			||||||
  static std::uniform_int_distribution<> dis(0, 255);
 | 
					  int const height = t_process_img.size().height;
 | 
				
			||||||
  return cv::Scalar(dis(t_gen), dis(t_gen), dis(t_gen));
 | 
					  int const width = t_process_img.size().width;
 | 
				
			||||||
 | 
					  int const shape_total_width = t_top_left.x + size;
 | 
				
			||||||
 | 
					  int const shape_total_height = t_top_left.y + size;
 | 
				
			||||||
 | 
					  if (int const diff = shape_total_height - height; diff > 0) {
 | 
				
			||||||
 | 
					    t_top_left.y -= diff + 1;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  if (int const diff = shape_total_width - width; diff > 0) {
 | 
				
			||||||
 | 
					    t_top_left.x -= diff + 1;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void newSquare1(cv::Mat &t_process_img, std::mt19937 &t_gen,
 | 
					cv::Scalar randomColor() {
 | 
				
			||||||
                randint &t_rand_pos) {
 | 
					  static std::uniform_int_distribution<> dis(0, 255);
 | 
				
			||||||
  const int square_size = t_rand_pos(t_gen);
 | 
					  return cv::Scalar(rand() % 255, rand() % 255, rand() % 255);
 | 
				
			||||||
  auto square_top_left = cv::Point{t_rand_pos(t_gen), t_rand_pos(t_gen)};
 | 
					}
 | 
				
			||||||
  draw_shape(t_process_img, square_top_left, square_size, randomColor(t_gen),
 | 
					
 | 
				
			||||||
             Shapes::Square);
 | 
					void newSquare1(cv::Mat &t_process_img, cv::Point &&t_top_left, int t_size) {
 | 
				
			||||||
 | 
					  adjustSize(t_process_img, t_top_left, t_size);
 | 
				
			||||||
 | 
					  draw_shape(t_process_img, t_top_left, t_size, randomColor(), Shapes::Square);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void threadedGetColor(cv::Mat &t_reference, ColorSet &t_colors, int t_h) {
 | 
					void threadedGetColor(cv::Mat &t_reference, ColorSet &t_colors, int t_h) {
 | 
				
			||||||
@ -60,61 +72,59 @@ ColorSet getColorSet(cv::Mat &t_reference) {
 | 
				
			|||||||
  return res;
 | 
					  return res;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void newSquare2(cv::Mat &t_process_img, std::mt19937 &t_gen,
 | 
					void newSquare2(cv::Mat &t_process_img, cv::Point &&t_top_left, int t_size,
 | 
				
			||||||
                ColorSet const &t_colors, randint &t_rand_pos,
 | 
					                Color const &t_color) {
 | 
				
			||||||
                randint &t_rand_color) {
 | 
					  draw_shape(t_process_img, t_top_left, t_size,
 | 
				
			||||||
  int const square_size = t_rand_pos(t_gen);
 | 
					             cv::Scalar{static_cast<double>(t_color[0]),
 | 
				
			||||||
  auto square_top_left = cv::Point{t_rand_pos(t_gen), t_rand_pos(t_gen)};
 | 
					                        static_cast<double>(t_color[1]),
 | 
				
			||||||
  const auto color = t_colors[t_rand_color(t_gen)];
 | 
					                        static_cast<double>(t_color[2])},
 | 
				
			||||||
  draw_shape(t_process_img, square_top_left, square_size,
 | 
					 | 
				
			||||||
             cv::Scalar{static_cast<double>(color[0]),
 | 
					 | 
				
			||||||
                        static_cast<double>(color[1]),
 | 
					 | 
				
			||||||
                        static_cast<double>(color[2])},
 | 
					 | 
				
			||||||
             Shapes::Square);
 | 
					             Shapes::Square);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
} // namespace methods_private
 | 
					} // namespace methods_private
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void method1(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations,
 | 
					void method1(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations) {
 | 
				
			||||||
             std::mt19937 &t_gen) {
 | 
					 | 
				
			||||||
  auto diff = euclidian_distance(t_reference, t_output);
 | 
					  auto diff = euclidian_distance(t_reference, t_output);
 | 
				
			||||||
  auto const max_size =
 | 
					 | 
				
			||||||
      std::max(t_reference.size().width, t_reference.size().height);
 | 
					 | 
				
			||||||
  randint dist(0, max_size);
 | 
					 | 
				
			||||||
  spdlog::debug("Beginning method1, initial difference: {}", diff);
 | 
					  spdlog::debug("Beginning method1, initial difference: {}", diff);
 | 
				
			||||||
  while (t_iterations > 0) {
 | 
					  while (t_iterations > 0 && diff >= 0) {
 | 
				
			||||||
    auto temp_image = t_output.clone();
 | 
					    auto temp_image = t_output.clone();
 | 
				
			||||||
    methods_private::newSquare1(temp_image, t_gen, dist);
 | 
					    int const rand_x = rand() % temp_image.size().width;
 | 
				
			||||||
    if (auto new_diff = euclidian_distance(t_reference, temp_image);
 | 
					    int const rand_y = rand() % temp_image.size().height;
 | 
				
			||||||
 | 
					    int const size = rand() % std::min(t_reference.size().width - rand_x,
 | 
				
			||||||
 | 
					                                       t_reference.size().height - rand_y);
 | 
				
			||||||
 | 
					    methods_private::newSquare1(temp_image, cv::Point{rand_x, rand_y}, size);
 | 
				
			||||||
 | 
					    if (auto const new_diff = euclidian_distance(t_reference, temp_image);
 | 
				
			||||||
        new_diff < diff) {
 | 
					        new_diff < diff) {
 | 
				
			||||||
      diff = new_diff;
 | 
					      diff = new_diff;
 | 
				
			||||||
      temp_image.copyTo(t_output);
 | 
					      temp_image.copyTo(t_output);
 | 
				
			||||||
      --t_iterations;
 | 
					      --t_iterations;
 | 
				
			||||||
      spdlog::debug("Iteration {}: diff {}", t_iterations, diff);
 | 
					      spdlog::debug("iteration:{} diff:{}", t_iterations, diff);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void method2(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations,
 | 
					void method2(cv::Mat &t_reference, cv::Mat &t_output, int t_iterations) {
 | 
				
			||||||
             std::mt19937 &t_gen) {
 | 
					 | 
				
			||||||
  auto diff = euclidian_distance(t_reference, t_output);
 | 
					  auto diff = euclidian_distance(t_reference, t_output);
 | 
				
			||||||
  auto const max_size =
 | 
					 | 
				
			||||||
      std::max(t_reference.size().width, t_reference.size().height);
 | 
					 | 
				
			||||||
  randint dist(0, max_size);
 | 
					 | 
				
			||||||
  spdlog::debug("Beginning method2, initial difference: {}", diff);
 | 
					  spdlog::debug("Beginning method2, initial difference: {}", diff);
 | 
				
			||||||
  auto const colors = methods_private::getColorSet(t_reference);
 | 
					
 | 
				
			||||||
  spdlog::debug("Running {} threads.", thread_nbr);
 | 
					  spdlog::debug("Running {} threads.", thread_nbr);
 | 
				
			||||||
 | 
					  auto const colors = methods_private::getColorSet(t_reference);
 | 
				
			||||||
  spdlog::debug("{} colors detected.", colors.size());
 | 
					  spdlog::debug("{} colors detected.", colors.size());
 | 
				
			||||||
  randint rand_color(0, colors.size());
 | 
					
 | 
				
			||||||
  while (t_iterations > 0) {
 | 
					  while (t_iterations > 0) {
 | 
				
			||||||
    auto temp_image = t_output.clone();
 | 
					    auto temp_image = t_output.clone();
 | 
				
			||||||
    methods_private::newSquare2(temp_image, t_gen, colors, dist, rand_color);
 | 
					    int const rand_x = rand() % temp_image.size().width;
 | 
				
			||||||
 | 
					    int const rand_y = rand() % temp_image.size().height;
 | 
				
			||||||
 | 
					    int const size = rand() % std::min(t_reference.size().width - rand_x,
 | 
				
			||||||
 | 
					                                       t_reference.size().height - rand_y);
 | 
				
			||||||
 | 
					    methods_private::newSquare2(temp_image, cv::Point{rand_x, rand_y}, size,
 | 
				
			||||||
 | 
					                                colors[rand() % colors.size()]);
 | 
				
			||||||
    if (auto new_diff = euclidian_distance(t_reference, temp_image);
 | 
					    if (auto new_diff = euclidian_distance(t_reference, temp_image);
 | 
				
			||||||
        new_diff < diff) {
 | 
					        new_diff < diff) {
 | 
				
			||||||
      diff = new_diff;
 | 
					      diff = new_diff;
 | 
				
			||||||
      temp_image.copyTo(t_output);
 | 
					      temp_image.copyTo(t_output);
 | 
				
			||||||
      --t_iterations;
 | 
					      --t_iterations;
 | 
				
			||||||
      spdlog::debug("Iteration {}: diff {}", t_iterations, diff);
 | 
					      spdlog::debug("iteration:{} diff:{}", t_iterations, diff);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user