萌新学習マニュアル:Shi-TOmasi角点検出


独学の対象:https://blog.csdn.net/dcrmg/article/details/52551637
Shi-TOmasはHarrisアルゴリズムの改良であり,効率も大幅に改善された.
まずはAPIをご紹介します
void goodFeaturesToTrack( InputArray image, 
                          OutputArray corners,
                          int maxCorners, 
                          double qualityLevel, double minDistance,
                          InputArray mask=noArray(), 
                          int blockSize=3,
                          bool useHarrisDetector=false, 
                          double k=0.04 );

アルゴリズムは、処理画像を式に従って設定しきい値より大きいすべての点を求めて1つのvectorに格納し、点数が設定した最大数を超えると、選択特徴が最も明らかな上位数を選択する
image:8ビットまたは32ビットの単一チャネル階調画像;
corners:位置点ベクトルで、検出された角点の座標を保存します.
maxCorners:検出可能な角点の数の最大値を定義します.
qualityLevel:検出されたコーナーの質量レベルで、コーナーフィーチャー値がqualityLevel*の最大フィーチャー値より小さいポイントは破棄されます.
minDistance:2つの角点間の最小間隔で、画素単位で;
mask:検出領域を指定し、画像全体を検出したら、maskを空のMat()にする.
blockSize:共分散行列を計算するときのウィンドウサイズ;
useHarrisDetector:Harris角点検出を使用するか、falseの場合はShi-TOmasi演算子を使用します.
k:Harris角点検出演算子用の中間パラメータを残し、一般的に経験値0.04~0.06をとる.8番目のパラメータがfalseの場合、このパラメータは機能しません.
RNG rng(1234);
rng.uniform(0,255)

これは擬似乱数を生成する方法であり、もちろん、生成する擬似乱数が小数(例えば0以上1未満)である場合はrngを呼び出す必要がある.uniform(0.,1.)つまり、2つの浮動小数点数タイプが入力されます.
#include
#include
using namespace std;
using namespace cv;
Mat src, gray_src;
int corner_num = 25;
int max_corner = 200;
const char* output_title = "ShiTomasi Detector";
RNG rng(1234);

void ShiTomas_Demo(int, void*);

int main(int argc, char** argv) {
	src = imread("C:/Users/pbiha/Desktop/image/2.png");
	if (src.empty()) {
		puts("Can't find the image...");
		return -1;
	}
	namedWindow("input", CV_WINDOW_AUTOSIZE);
	imshow("input", src);
	cvtColor(src, gray_src, COLOR_BGR2GRAY);
	namedWindow(output_title, CV_WINDOW_AUTOSIZE);

	createTrackbar("Num corner:", output_title, &corner_num, max_corner, ShiTomas_Demo);
	ShiTomas_Demo(0, 0);
	waitKey(0);
	return 0;
}
void ShiTomas_Demo(int, void*) {
	if (corner_num < 5)corner_num = 5;
	vectorcorners;
	double qualityLevel = 0.01;
	double minDistance = 15;
	int blockSize = 3;
	bool useHarris = false;
	double k = 0.04;
	
	Mat resultImg = src.clone();

	goodFeaturesToTrack(gray_src, corners, corner_num, qualityLevel, minDistance, Mat(), blockSize, useHarris, k);
	printf("%d
", corners.size()); for (int i = 0; i < corners.size(); i++) { circle(resultImg, corners[i], 2, Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), 2, 8, 0); } imshow(output_title, resultImg); }