printf("ho_tari\n");

Chapter7 : 필터링 본문

OpenCV

Chapter7 : 필터링

호타리 2023. 9. 14. 15:51

<OpenCV_Projects.cpp>

#include <opencv2/opencv.hpp>

extern void filter_embossing();
extern void filter_blurring();
extern void filter_gaussian();
extern void filter_unsharp_mask();

int main() 
{
    std::cout << CV_VERSION << std::endl;

    //filter_embossing();
    //filter_blurring();
    //filter_gaussian();
    filter_unsharp_mask();
}

 

<filter_embossing.cpp>

#pragma once
#include <opencv2/opencv.hpp>

void filter_embossing()
{
	cv::Mat src = cv::imread("rose.bmp", cv::IMREAD_GRAYSCALE);
	
	if (src.empty()) return;

	float filter_data[] = { -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f };

	cv::Mat emboss_kernel(3, 3, CV_32FC1, filter_data);

	cv::Mat dst;
	cv::filter2D(src, dst, -1, emboss_kernel, cv::Point(-1, -1), 120 /*좀 더 밝게*/);
	cv::imshow("SRC", src);
	cv::imshow("DST", dst);
	cv::waitKey();
	cv::destroyAllWindows();
}

<compile 결과>

 

<filter_blurring.cpp>

#pragma once
#include <opencv2/opencv.hpp>

void filter_blurring()
{
	cv::Mat src = cv::imread("rose.bmp", cv::IMREAD_GRAYSCALE);

	if (src.empty()) return;

	cv::Mat dst1;
	cv::Mat dst3;

	float blur_filter[] = { 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f, 1 / 9.f };

	cv::Mat dst2(3, 3, CV_32FC1, blur_filter);	// 3 x 3 평균값 필터
	cv::filter2D(src, dst1, -1, dst2, cv::Point(-1, -1), 0);
	
	cv::imshow("SRC", src);
	cv::imshow("DST1", dst1);
	cv::waitKey();

	for (int ksize = 3; ksize <= 7; ksize += 2)
	{
		cv::blur(src, dst3, cv::Size(ksize, ksize));
		cv::String desc = cv::format("Blur : %d X %d", ksize, ksize);
		cv::putText(dst3, desc, cv::Point(10, 30), cv::FONT_HERSHEY_SIMPLEX, 1.0, cv::Scalar(255), 1, cv::LINE_AA);
		cv::imshow("DST3", dst3);
		cv::waitKey();
	}

	cv::destroyAllWindows();
}

<compile 결과>

키보드 아무키를 누르면 블러가 점점 심해진다

 

<filter_gaussian.cpp>

#pragma once
#include <opencv2/opencv.hpp>

void filter_gaussian()
{
	cv::Mat src = cv::imread("rose.bmp", cv::IMREAD_GRAYSCALE);

	if (src.empty()) return;

	cv::Mat dst;

	for (int sigma = 1; sigma <= 5; ++sigma)
	{
		cv::GaussianBlur(src, dst, cv::Size(), static_cast<double>(sigma));
		cv::String text = cv::format("Sigma : %d", sigma);
		cv::putText(dst, text, cv::Point(10, 30), cv::FONT_HERSHEY_PLAIN, 1.0, cv::Scalar(255), 1, cv::LINE_AA);
		cv::imshow(text, dst);
		cv::waitKey();
	}
	cv::destroyAllWindows();
}

<compile 결과>

 

<filter_unsharp_mask.cpp>

#pragma once
#include <opencv2/opencv.hpp>

void filter_unsharp_mask()
{
	cv::Mat src = cv::imread("rose.bmp", cv::IMREAD_GRAYSCALE);

	if (src.empty()) return;

	cv::imshow("SRC", src);
	cv::Mat blurred;
	float alpha = 1.0f;
	for (int sigma = 1; sigma <= 5; ++sigma)
	{
		cv::GaussianBlur(src, blurred, cv::Size(), sigma);
		cv::Mat dst = (1 + alpha) * src - (alpha * blurred);
		cv::String text = cv::format("Sigma : %d", sigma);
		cv::putText(dst, text, cv::Point(10, 30), cv::FONT_HERSHEY_SIMPLEX, 1.0, cv::Scalar(255), 1, cv::LINE_AA);
		cv::imshow(text, dst);
		cv::waitKey();
	}
	cv::destroyAllWindows();
}

<compile 결과>

 

<noise_gaussian.cpp>

#pragma once
#include <opencv2/opencv.hpp>

using namespace std;
using namespace cv;

//가우시안 잡음 추가 함수
void noise_gaussian() 
{
	Mat src = imread("lenna.bmp", IMREAD_GRAYSCALE);
	if (src.empty()) return;
	Mat dst;
	for (int stddev = 10; stddev <= 30; stddev += 10) 
    {
		Mat noise(src.size(), CV_32FC1);
		randn(noise, 0, stddev); //평균이 0이고 표준편차는 10부터 30이하의 값
		add(src, noise, dst, noArray(), CV_8UC1);
		String text = format("stddev = %d", stddev);
		putText(dst, text, Point(10, 30), FONT_HERSHEY_SIMPLEX, 1.0, Scalar(255), 1, LINE_AA);
		imshow("DST", dst);
		waitKey();
	}
	destroyAllWindows();
}

<compile 결과>

 

<filter_bilateral.cpp>

#pragma once
#include <opencv2/opencv.hpp>

using namespace std;
using namespace cv;

//양방향 필터 함수
void filter_bilateral() 
{
	Mat src = imread("lenna.bmp", IMREAD_GRAYSCALE);
	if (src.empty()) return;
	Mat noise(src.size(), CV_32SC1);
	randn(noise, 0, 5);                  //평균 0, 표준편차 5
	add(src, noise, src, Mat(), CV_8U);
	
	Mat dst1;
	GaussianBlur(src, dst1, Size(), 5);    //gaussian blur를 사용하면 주로엣지부분이 필터링된다. (sigma5)

	Mat dst2;
	bilateralFilter(src, dst2, -1 /* 이웃 픽셀과의 거리를 자동으로 잡아준다. */, 10, 5);  //bilateral Filter을 사용하면 엣지를 제외한 나머지부분이 주로 필터링된다.

	imshow("SRC", src);
	imshow("dst1", dst1);
	imshow("dst2", dst2);
	waitKey();
	destroyAllWindows();
}

<compile 결과>

 

<filter_median.cpp>

#pragma once
#include <opencv2/opencv.hpp>

using namespace std;
using namespace cv;

//미디언 필터 함수
void filter_median() 
{
	Mat src = imread("lenna.bmp", IMREAD_GRAYSCALE);
	if (src.empty()) return;
	//salt & pepper 노이즈 방식
	int num = (int)(src.total() * 0.1);
	for (int i = 0; i < num; i++) 
    {
		int x = rand() % src.cols;
		int y = rand() % src.rows;
		src.at<uchar>(y, x) = (i % 2) * 255;   // 짝수이면 검은점, 홀수이면 흰점
	}
	Mat dst1;
	GaussianBlur(src, dst1, Size(), 1);

	Mat dst2;
	medianBlur(src, dst2, 3);

	imshow("SRC", src);    // 원본에 salt & pepper이 추가된 이미지
	imshow("dst1", dst1);	// gaussian blur 가 적용된 이미지
	imshow("dst2", dst2);   // median blur가 적용된 이미지
	waitKey();
	destroyAllWindows();
}

<compile 결과>