#include <opencv2/opencv.hpp>
#include <opencv2/highgui.hpp>
#include <iostream>
using namespace cv;
using namespace std;


void maded_prewitt(const Mat& image, Mat& result, int thresh) {

	// 수직마스크
	Mat maskX = (Mat_<double>(3, 3) << -1, 0, 1, -1, 0, 1, -1, 0, 1);
	// 수평마스크
	Mat maskY = (Mat_<double>(3, 3) << 1, 1, 1, 0, 0, 0, -1, -1, -1);

	int filterOffset = 3 / 2;

	result = Mat::zeros(image.rows - filterOffset * 2, image.cols - filterOffset * 2, image.type());

	double sumEdgeX;
	double sumEdgeY;
	double magnitude;

	for (int yimage = filterOffset; yimage < image.rows - filterOffset; ++yimage) {
		for (int ximage = filterOffset; ximage < image.cols - filterOffset; ++ximage) {

			sumEdgeX = 0;
			sumEdgeY = 0;
			for (int ymask = -filterOffset; ymask <= filterOffset; ++ymask) {
				for (int xmask = -filterOffset; xmask <= filterOffset; ++xmask) {
					sumEdgeX += image.at<uchar>(yimage + ymask, ximage + xmask) * maskX.at<double>(filterOffset + ymask, filterOffset + xmask);
					sumEdgeY += image.at<uchar>(yimage + ymask, ximage + xmask) * maskY.at<double>(filterOffset + ymask, filterOffset + xmask);
				}
			}
			magnitude = sqrt(pow(sumEdgeY, 2) + pow(sumEdgeX, 2));
			result.at<uchar>(yimage - filterOffset, ximage - filterOffset) = ((magnitude > thresh) ? 255 : 0);
		}
	}

}

void maded_sobel(const Mat& image, Mat& result, int thresh) {

	// 수직마스크
	Mat maskX = (Mat_<double>(3, 3) << -1, 0, 1, -2, 0, 2, -1, 0, 1);
	// 수평마스크
	Mat maskY = (Mat_<double>(3, 3) << 1, 2, 1, 0, 0, 0, -1, -2, -1);

	int filterOffset = 3 / 2;

	result = Mat::zeros(image.rows - filterOffset * 2, image.cols - filterOffset * 2, image.type());

	double sumEdgeX;
	double sumEdgeY;
	double magnitude;

	for (int yimage = filterOffset; yimage < image.rows - filterOffset; ++yimage) {
		for (int ximage = filterOffset; ximage < image.cols - filterOffset; ++ximage) {

			sumEdgeX = 0;
			sumEdgeY = 0;
			for (int ymask = -filterOffset; ymask <= filterOffset; ++ymask) {
				for (int xmask = -filterOffset; xmask <= filterOffset; ++xmask) {
					sumEdgeX += image.at<uchar>(yimage + ymask, ximage + xmask) * maskX.at<double>(filterOffset + ymask, filterOffset + xmask);
					sumEdgeY += image.at<uchar>(yimage + ymask, ximage + xmask) * maskY.at<double>(filterOffset + ymask, filterOffset + xmask);
				}
			}
			magnitude = sqrt(pow(sumEdgeY, 2) + pow(sumEdgeX, 2));
			result.at<uchar>(yimage - filterOffset, ximage - filterOffset) = ((magnitude > thresh) ? 255 : 0);
		}
	}

}

int main()
{
	Mat src, sobel_1;
	Mat grad, prewitt;

	src = imread("dog.png", IMREAD_GRAYSCALE);
	if (src.empty()) { return -1; }

	imshow("Image", src);
	maded_sobel(src, sobel_1, 100);
	imshow("sobel", sobel_1);
	maded_prewitt(src, prewitt, 100);
	imshow("prewitt", prewitt);

	waitKey(0);
	return 0;


}

왼쪽이 소벨 오른쪽이 프리윗 마스크가 적용된 이미지입니다.

 

+ Recent posts