OpenCV 5.0.0
Open Source Computer Vision
読み込み中...
検索中...
見つかりません
🤖 AIによる機械翻訳(非公式) — これは OpenCV 5.0.0 公式リファレンス(英語)を AI (Claude) で自動翻訳したものです。訳に誤りを含む場合があります。正確な情報は 公式英語版(原文) を参照してください。
特徴検出

詳細説明

クラス

class  cv::LineSegmentDetector
 線分検出器クラス。 詳細...
 

列挙型

enum  cv::HoughModes {
  cv::HOUGH_STANDARD = 0 ,
  cv::HOUGH_PROBABILISTIC = 1 ,
  cv::HOUGH_MULTI_SCALE = 2 ,
  cv::HOUGH_GRADIENT = 3 ,
  cv::HOUGH_GRADIENT_ALT = 4
}
 ハフ変換のバリアント。 続きを読む...
 

関数

void cv::Canny (InputArray dx, InputArray dy, OutputArray edges, double threshold1, double threshold2, bool L2gradient=false)
 
void cv::Canny (InputArray image, OutputArray edges, double threshold1, double threshold2, int apertureSize=3, bool L2gradient=false)
 Cannyアルゴリズム [50] を用いて画像中のエッジを検出する。
 
void cv::cornerEigenValsAndVecs (InputArray src, OutputArray dst, int blockSize, int ksize, int borderType=BORDER_DEFAULT)
 コーナー検出のために画像ブロックの固有値と固有ベクトルを計算する。
 
void cv::cornerHarris (InputArray src, OutputArray dst, int blockSize, int ksize, double k, int borderType=BORDER_DEFAULT)
 Harrisコーナー検出器。
 
void cv::cornerMinEigenVal (InputArray src, OutputArray dst, int blockSize, int ksize=3, int borderType=BORDER_DEFAULT)
 コーナー検出のために勾配行列の最小固有値を計算する。
 
void cv::cornerSubPix (InputArray image, InputOutputArray corners, Size winSize, Size zeroZone, TermCriteria criteria)
 コーナー位置を精密化する。
 
Ptr< LineSegmentDetectorcv::createLineSegmentDetector (LineSegmentDetectorModes refine=LSD_REFINE_STD, double scale=0.8, double sigma_scale=0.6, double quant=2.0, double ang_th=22.5, double log_eps=0, double density_th=0.7, int n_bins=1024)
 LineSegmentDetector オブジェクトへのスマートポインタを生成して初期化する。
 
void cv::HoughCircles (InputArray image, OutputArray circles, int method, double dp, double minDist, double param1=100, double param2=100, int minRadius=0, int maxRadius=0)
 Hough変換を用いてグレースケール画像内の円を検出する。
 
void cv::HoughLines (InputArray image, OutputArray lines, double rho, double theta, int threshold, double srn=0, double stn=0, double min_theta=0, double max_theta=CV_PI, bool use_edgeval=false)
 標準Hough変換を用いて2値画像内の直線を検出する。
 
void cv::HoughLinesP (InputArray image, OutputArray lines, double rho, double theta, int threshold, double minLineLength=0, double maxLineGap=0)
 確率的Hough変換を用いて2値画像内の線分を検出する。
 
void cv::HoughLinesPointSet (InputArray point, OutputArray lines, int lines_max, int threshold, double min_rho, double max_rho, double rho_step, double min_theta, double max_theta, double theta_step)
 標準Hough変換を用いて点群から直線を検出する。
 
void cv::preCornerDetect (InputArray src, OutputArray dst, int ksize, int borderType=BORDER_DEFAULT)
 コーナー検出のための特徴マップを計算する。
 

列挙型詳解

◆ HoughModes

#include <opencv2/imgproc.hpp>

ハフ変換のバリアント。

列挙値
HOUGH_STANDARD 
Python: cv.HOUGH_STANDARD

古典的または標準的なHough変換。各直線は2つの浮動小数点数 \((\rho, \theta)\) で表される。ここで \(\rho\) は (0,0) 点と直線との距離、\(\theta\) はx軸と直線の法線との間の角度である。したがって、行列は(生成されるシーケンスは)CV_32FC2 型でなければならない。

HOUGH_PROBABILISTIC 
Python: cv.HOUGH_PROBABILISTIC

確率的Hough変換(画像にいくつかの長い線分が含まれる場合に効率的)。直線全体ではなく線分を返す。各線分は始点と終点で表され、行列は(生成されるシーケンスは)CV_32SC4 型でなければならない。

HOUGH_MULTI_SCALE 
Python: cv.HOUGH_MULTI_SCALE

古典的なハフ変換のマルチスケール版。直線は HOUGH_STANDARD と同じ方法でエンコードされる。

HOUGH_GRADIENT 
Python: cv.HOUGH_GRADIENT

基本的には 21HT[322] で説明されている。

HOUGH_GRADIENT_ALT 
Python: cv.HOUGH_GRADIENT_ALT

より高い精度を得るための HOUGH_GRADIENT の派生版

関数詳解

◆ Canny() [1/2]

void cv::Canny ( InputArray dx,
InputArray dy,
OutputArray edges,
double threshold1,
double threshold2,
bool L2gradient = false )
Python:
cv.Canny(image, threshold1, threshold2[, edges[, apertureSize[, L2gradient]]]) -> edges
cv.Canny(dx, dy, threshold1, threshold2[, edges[, L2gradient]]) -> edges

#include <opencv2/imgproc.hpp>

これは利便性のために提供されているオーバーロードされたメンバ関数である。上記の関数とは、受け取る引数のみが異なる。

カスタムの画像勾配を用いて、Cannyアルゴリズムにより画像のエッジを検出する。

引数
dx入力画像の16ビットのx方向微分(CV_16SC1 または CV_16SC3)。
dy入力画像の16ビットのy方向微分(dx と同じ型)。
edges出力されるエッジマップ。シングルチャンネルの8ビット画像で、image と同じサイズを持つ。
threshold1ヒステリシス処理のための第1のしきい値。
threshold2ヒステリシス処理のための第2のしきい値。
L2gradient画像の勾配の大きさを計算する際に、より正確な \(L_2\) ノルム \(=\sqrt{(dI/dx)^2 + (dI/dy)^2}\) を使用すべきか( L2gradient=true )、あるいはデフォルトの \(L_1\) ノルム \(=|dI/dx|+|dI/dy|\) で十分か( L2gradient=false )を示すフラグ。

◆ Canny() [2/2]

void cv::Canny ( InputArray image,
OutputArray edges,
double threshold1,
double threshold2,
int apertureSize = 3,
bool L2gradient = false )
Python:
cv.Canny(image, threshold1, threshold2[, edges[, apertureSize[, L2gradient]]]) -> edges
cv.Canny(dx, dy, threshold1, threshold2[, edges[, L2gradient]]) -> edges

#include <opencv2/imgproc.hpp>

Cannyアルゴリズム [50] を用いて画像のエッジを検出する。

この関数は入力画像からエッジを検出し、Cannyアルゴリズムを用いて出力マップ edges にマークする。threshold1 と threshold2 のうち小さい方の値はエッジの連結に使われる。大きい方の値は強いエッジの初期セグメントを見つけるために使われる。https://en.wikipedia.org/wiki/Canny_edge_detector を参照。

引数
image8ビット入力画像。
edges出力されるエッジマップ。シングルチャンネルの8ビット画像で、image と同じサイズを持つ。
threshold1ヒステリシス処理のための第1のしきい値。
threshold2ヒステリシス処理のための第2のしきい値。
apertureSizeSobel 演算子のアパーチャサイズ。
L2gradient画像の勾配の大きさを計算する際に、より正確な \(L_2\) ノルム \(=\sqrt{(dI/dx)^2 + (dI/dy)^2}\) を使用すべきか( L2gradient=true )、あるいはデフォルトの \(L_1\) ノルム \(=|dI/dx|+|dI/dy|\) で十分か( L2gradient=false )を示すフラグ。

◆ cornerEigenValsAndVecs()

void cv::cornerEigenValsAndVecs ( InputArray src,
OutputArray dst,
int blockSize,
int ksize,
int borderType = BORDER_DEFAULT )
Python:
cv.cornerEigenValsAndVecs(src, blockSize, ksize[, dst[, borderType]]) -> dst

#include <opencv2/imgproc.hpp>

コーナー検出のために画像ブロックの固有値と固有ベクトルを計算する。

各ピクセル \(p\) について、関数 cornerEigenValsAndVecs は blockSize \(\times\) blockSize の近傍 \(S(p)\) を考える。近傍にわたる微分の共分散行列を次のように計算する:

\[M = \begin{bmatrix} \sum _{S(p)}(dI/dx)^2 & \sum _{S(p)}dI/dx dI/dy \\ \sum _{S(p)}dI/dx dI/dy & \sum _{S(p)}(dI/dy)^2 \end{bmatrix}\]

ここで、微分はSobelオペレータを用いて計算される。

その後、\(M\) の固有ベクトルと固有値を求め、それらを \((\lambda_1, \lambda_2, x_1, y_1, x_2, y_2)\) として出力画像に格納する。ここで

  • \(\lambda_1, \lambda_2\) は \(M\) のソートされていない固有値
  • \(x_1, y_1\) は \(\lambda_1\) に対応する固有ベクトル
  • \(x_2, y_2\) は \(\lambda_2\) に対応する固有ベクトル

この関数の出力は、ロバストなエッジ検出やコーナー検出に利用できる。

引数
src入力のシングルチャンネル8ビットまたは浮動小数点画像。
dst結果を格納する画像。src と同じサイズで、型は CV_32FC(6) である。
blockSize近傍サイズ(以下の詳細を参照)。
ksizeSobel 演算子のアパーチャ引数。
borderTypeピクセルの外挿方法。BorderTypes を参照。BORDER_WRAP はサポートされていない。
参照
cornerMinEigenVal, cornerHarris, preCornerDetect

◆ cornerHarris()

void cv::cornerHarris ( InputArray src,
OutputArray dst,
int blockSize,
int ksize,
double k,
int borderType = BORDER_DEFAULT )
Python:
cv.cornerHarris(src, blockSize, ksize, k[, dst[, borderType]]) -> dst

#include <opencv2/imgproc.hpp>

Harrisコーナー検出器。

この関数は画像に対してHarrisコーナー検出器を実行する。cornerMinEigenVal や cornerEigenValsAndVecs と同様に、各ピクセル \((x, y)\) について \(\texttt{blockSize} \times \texttt{blockSize}\) の近傍にわたる \(2\times2\) の勾配共分散行列 \(M^{(x,y)}\) を計算する。次に、以下の特性値を計算する:

\[\texttt{dst} (x,y) = \mathrm{det} M^{(x,y)} - k \cdot \left ( \mathrm{tr} M^{(x,y)} \right )^2\]

画像中のコーナーは、この応答マップの局所最大値として求めることができる。

引数
src入力のシングルチャンネル8ビットまたは浮動小数点画像。
dstHarrisコーナー検出器の応答値を格納する画像。型は CV_32FC1 で、src と同じサイズを持つ。
blockSize近傍サイズ(cornerEigenValsAndVecs の詳細を参照)。
ksizeSobel 演算子のアパーチャ引数。
kHarris検出器の自由パラメータ。上記の式を参照。
borderTypeピクセルの外挿方法。BorderTypes を参照。BORDER_WRAP はサポートされていない。

◆ cornerMinEigenVal()

void cv::cornerMinEigenVal ( InputArray src,
OutputArray dst,
int blockSize,
int ksize = 3,
int borderType = BORDER_DEFAULT )
Python:
cv.cornerMinEigenVal(src, blockSize[, dst[, ksize[, borderType]]]) -> dst

#include <opencv2/imgproc.hpp>

コーナー検出のために勾配行列の最小固有値を計算する。

この関数は cornerEigenValsAndVecs に似ているが、微分の共分散行列の最小固有値、すなわち cornerEigenValsAndVecs の説明にある数式での \(\min(\lambda_1, \lambda_2)\) のみを計算して格納する。

引数
src入力のシングルチャンネル8ビットまたは浮動小数点画像。
dst最小固有値を格納する画像。型は CV_32FC1 で、src と同じサイズを持つ。
blockSize近傍サイズ(cornerEigenValsAndVecs の詳細を参照)。
ksizeSobel 演算子のアパーチャ引数。
borderTypeピクセルの外挿方法。BorderTypes を参照。BORDER_WRAP はサポートされていない。

◆ cornerSubPix()

void cv::cornerSubPix ( InputArray image,
InputOutputArray corners,
Size winSize,
Size zeroZone,
TermCriteria criteria )
Python:
cv.cornerSubPix(image, corners, winSize, zeroZone, criteria) -> corners

#include <opencv2/imgproc.hpp>

コーナー位置をリファインする。

この関数は、[99] で説明され、下図に示されているように、コーナーまたは放射状のサドル点のサブピクセル精度の位置を求めるために反復処理を行う。

image

サブピクセル精度のコーナー位置検出は、中心 \(q\) から \(q\) の近傍内にある点 \(p\) へのすべてのベクトルが、画像および測定のノイズの範囲内で \(p\) における画像勾配と直交するという観察に基づいている。次の式を考える:

\[\epsilon _i = {DI_{p_i}}^T \cdot (q - p_i)\]

ここで \({DI_{p_i}}\) は \(q\) の近傍内の点 \(p_i\) の1つにおける画像勾配である。\(q\) の値は \(\epsilon_i\) が最小化されるように求める。\(\epsilon_i\) をゼロに設定することで連立方程式を立てることができる:

\[\sum _i(DI_{p_i} \cdot {DI_{p_i}}^T) \cdot q - \sum _i(DI_{p_i} \cdot {DI_{p_i}}^T \cdot p_i)\]

ここで勾配は \(q\) の近傍(「探索ウィンドウ」)内で合計される。第1の勾配項を \(G\)、第2の勾配項を \(b\) と呼ぶと、次のようになる:

\[q = G^{-1} \cdot b\]

アルゴリズムはこの新しい中心 \(q\) に近傍ウィンドウの中心を設定し、中心が設定したしきい値の範囲内に収まるまで反復する。

引数
image入力のシングルチャンネル8ビットまたは浮動小数点画像。
corners入力コーナーの初期座標。精緻化された座標は出力として提供される。
winSize探索ウィンドウの片側の長さの半分。例えば winSize=Size(5,5) の場合、\((5*2+1) \times (5*2+1) = 11 \times 11\) の探索ウィンドウが使われる。
zeroZone探索領域の中央に設ける、以下の式での総和を行わないデッドゾーンのサイズの半分。これは自己相関行列の特異性を回避するために用いられることがある。値 (-1,-1) はそのようなサイズが存在しないことを示す。
criteriaコーナー精緻化の反復処理を終了する基準。すなわち、コーナー位置の精緻化処理は、criteria.maxCount 回の反復後、または反復中にコーナー位置の移動量が criteria.epsilon 未満になったときに停止する。

◆ createLineSegmentDetector()

Ptr< LineSegmentDetector > cv::createLineSegmentDetector ( LineSegmentDetectorModes refine = LSD_REFINE_STD,
double scale = 0.8,
double sigma_scale = 0.6,
double quant = 2.0,
double ang_th = 22.5,
double log_eps = 0,
double density_th = 0.7,
int n_bins = 1024 )
Python:
cv.createLineSegmentDetector([, refine[, scale[, sigma_scale[, quant[, ang_th[, log_eps[, density_th[, n_bins]]]]]]]]) -> retval

#include <opencv2/imgproc.hpp>

LineSegmentDetector オブジェクトへのスマートポインタを生成し、初期化する。

LineSegmentDetector アルゴリズムは標準的な値を用いて定義される。これらを編集したいのは上級ユーザーだけであり、自身のアプリケーション向けに調整するために用いる。

引数
refine検出された線分を絞り込む方法。LineSegmentDetectorModes を参照
scale直線の検出に使用する画像のスケール。Range (0..1]。
sigma_scaleガウシアンフィルタのシグマ。sigma = sigma_scale/scale として計算される。
quant勾配ノルムの量子化誤差に対する境界値。
ang_th勾配角度の許容誤差(度)。
log_eps検出のしきい値: -log10(NFA) > log_eps。高度な精緻化を選択した場合にのみ使用される。
density_th外接矩形内における整列した領域点の最小密度。
n_bins勾配係数の擬似順序付けにおけるビン数。

◆ HoughCircles()

void cv::HoughCircles ( InputArray image,
OutputArray circles,
int method,
double dp,
double minDist,
double param1 = 100,
double param2 = 100,
int minRadius = 0,
int maxRadius = 0 )
Python:
cv.HoughCircles(image, method, dp, minDist[, circles[, param1[, param2[, minRadius[, maxRadius]]]]]) -> circles

#include <opencv2/imgproc.hpp>

Hough変換を用いてグレースケール画像から円を検出する。

この関数は、ハフ変換の改良版を用いてグレースケール画像中の円を検出する。

例: :

#include <math.h>
using namespace cv;
using namespace std;
int main(int argc, char** argv)
{
Mat img, gray;
if( argc != 2 || !(img=imread(argv[1], IMREAD_COLOR)).data)
return -1;
cvtColor(img, gray, COLOR_BGR2GRAY);
// smooth it, otherwise a lot of false circles may be detected
GaussianBlur( gray, gray, Size(9, 9), 2, 2 );
vector<Vec3f> circles;
HoughCircles(gray, circles, HOUGH_GRADIENT,
2, gray.rows/4, 200, 100 );
for( size_t i = 0; i < circles.size(); i++ )
{
Point center(cvRound(circles[i][0]), cvRound(circles[i][1]));
int radius = cvRound(circles[i][2]);
// draw the circle center
circle( img, center, 3, Scalar(0,255,0), -1, 8, 0 );
// draw the circle outline
circle( img, center, radius, Scalar(0,0,255), 3, 8, 0 );
}
namedWindow( "circles", 1 );
imshow( "circles", img );
waitKey(0);
return 0;
}
Comma-separated Matrix Initializer.
Definition mat.hpp:964
int rows
the number of rows and columns or (-1, -1) when the matrix has more than 2 dimensions
Definition mat.hpp:2488
Template class for specifying the size of an image or rectangle.
Definition types.hpp:338
int cvRound(double value)
Rounds floating-point number to the nearest integer.
Definition fast_math.hpp:200
Mat imread(const String &filename, int flags=IMREAD_COLOR_BGR)
Loads an image from a file.
void cvtColor(InputArray src, OutputArray dst, int code, int dstCn=0, AlgorithmHint hint=cv::ALGO_HINT_DEFAULT)
Converts an image from one color space to another.
void HoughCircles(InputArray image, OutputArray circles, int method, double dp, double minDist, double param1=100, double param2=100, int minRadius=0, int maxRadius=0)
Finds circles in a grayscale image using the Hough transform.
void GaussianBlur(InputArray src, OutputArray dst, Size ksize, double sigmaX, double sigmaY=0, int borderType=BORDER_DEFAULT, AlgorithmHint hint=cv::ALGO_HINT_DEFAULT)
Blurs an image using a Gaussian filter.
int main(int argc, char *argv[])
Definition highgui_qt.cpp:3
Definition core.hpp:107
STL namespace.
覚え書き
通常、この関数は円の中心をうまく検出する。しかし、正しい半径を見つけられないことがある。半径の範囲( minRadius と maxRadius )が分かっている場合は、それを指定することで関数を支援できる。あるいは、HOUGH_GRADIENT メソッドの場合、maxRadius を負の数に設定すると半径の探索を行わずに中心のみを返すので、別途の手続きを用いて正しい半径を求めることができる。

また、画像がすでに滑らかでない限り、少し平滑化しておくと役立つ。例えば、7x7のカーネルと1.5x1.5のシグマによる GaussianBlur() や、それに類する平滑化が役立つことがある。

引数
image8ビット、シングルチャンネルのグレースケール入力画像。
circles検出された円の出力ベクトル。各ベクトルは3要素または4要素の浮動小数点ベクトル \((x, y, radius)\) または \((x, y, radius, votes)\) として符号化される。
method検出方法。HoughModes を参照。利用可能な方法は HOUGH_GRADIENTHOUGH_GRADIENT_ALT である。
dpアキュムレータの解像度と画像の解像度の逆比。例えば dp=1 の場合、アキュムレータは入力画像と同じ解像度を持つ。dp=2 の場合、アキュムレータの幅と高さは半分になる。HOUGH_GRADIENT_ALT では、非常に小さな円を検出する必要がある場合を除き、推奨値は dp=1.5 である。
minDist検出される円の中心間の最小距離。この引数が小さすぎると、真の円に加えて複数の近接した円が誤検出されることがある。大きすぎると、いくつかの円が見落とされることがある。
param11番目の方法固有のパラメータ。HOUGH_GRADIENT および HOUGH_GRADIENT_ALT の場合、Cannyエッジ検出器に渡される2つのしきい値のうち高い方の値である(低い方はその半分になる)。なお、HOUGH_GRADIENT_ALT は画像微分の計算に Scharr アルゴリズムを使用するため、しきい値は通常より高く、適正露出でコントラストのある画像では 300 程度に設定するのが普通である。
param22番目の方法固有のパラメータ。HOUGH_GRADIENT の場合、これは検出段階における円の中心に対するアキュムレータのしきい値である。小さいほど多くの偽の円が検出されやすくなる。アキュムレータ値が大きいものに対応する円が先に返される。HOUGH_GRADIENT_ALT アルゴリズムの場合、これは円の「完全度」を表す指標である。1に近いほど、アルゴリズムが選ぶ円の形状はより良くなる。ほとんどの場合 0.9 で問題ない。小さな円をより良く検出したい場合は 0.85、0.8、あるいはそれ以下に下げてよい。ただしその場合は、多くの偽の円を避けるために探索範囲 [minRadius, maxRadius] を制限することも試みるとよい。
minRadius円の最小半径。
maxRadius円の最大半径。<= 0 の場合は画像の最大寸法が使われる。< 0 の場合、HOUGH_GRADIENT は半径を求めずに中心を返す。HOUGH_GRADIENT_ALT は常に円の半径を計算する。
参照
fitEllipse, minEnclosingCircle

◆ HoughLines()

void cv::HoughLines ( InputArray image,
OutputArray lines,
double rho,
double theta,
int threshold,
double srn = 0,
double stn = 0,
double min_theta = 0,
double max_theta = CV_PI,
bool use_edgeval = false )
Python:
cv.HoughLines(image, rho, theta, threshold[, lines[, srn[, stn[, min_theta[, max_theta[, use_edgeval]]]]]]) -> lines

#include <opencv2/imgproc.hpp>

標準的なハフ変換を用いて、2値画像中の直線を検出する。

この関数は、直線検出のための標準的または標準的マルチスケールのハフ変換アルゴリズムを実装している。ハフ変換の分かりやすい解説については https://homepages.inf.ed.ac.uk/rbf/HIPR2/hough.htm を参照。

引数
image8ビット、シングルチャンネルの2値入力画像。この画像は関数によって変更されることがある。
lines直線の出力ベクトル。各直線は2要素または3要素のベクトル \((\rho, \theta)\) または \((\rho, \theta, \textrm{votes})\) で表される。ここで \(\rho\) は座標原点 \((0,0)\)(画像の左上隅)からの距離、\(\theta\) はラジアン単位の直線の回転角( \(0 \sim \textrm{vertical line}, \pi/2 \sim \textrm{horizontal line}\) )、\(\textrm{votes}\) はアキュムレータの値である。
rhoアキュムレータの距離解像度(ピクセル単位)。
thetaアキュムレータの角度解像度(ラジアン単位)。
thresholdアキュムレータのしきい値引数。十分な票数 ( \(>\texttt{threshold}\) ) を得た直線のみが返される。
srnマルチスケールHough変換の場合、距離分解能 rho に対する除数。粗いアキュムレータの距離分解能は rho、精密なアキュムレータの分解能は rho/srn である。srn=0 かつ stn=0 の両方の場合、古典的なHough変換が使用される。それ以外の場合、これらのパラメータは両方とも正でなければならない。
stnマルチスケールHough変換の場合、距離分解能 theta に対する除数。
min_theta標準およびマルチスケールHough変換の場合、直線を検出する最小角度。0 と max_theta の間でなければならない。
max_theta標準およびマルチスケールHough変換の場合、角度の上限。min_theta と CV_PI の間でなければならない。アキュムレータ内の実際の最大角度は、パラメータ min_theta と theta によっては max_theta よりわずかに小さくなる場合がある。
use_edgeval重み付きHough変換を使用したい場合は true。

◆ HoughLinesP()

void cv::HoughLinesP ( InputArray image,
OutputArray lines,
double rho,
double theta,
int threshold,
double minLineLength = 0,
double maxLineGap = 0 )
Python:
cv.HoughLinesP(image, rho, theta, threshold[, lines[, minLineLength[, maxLineGap]]]) -> lines

#include <opencv2/imgproc.hpp>

確率的ハフ変換を用いて二値画像中の線分を検出する。

この関数は、[192] で説明されている、線分検出のための確率的ハフ変換アルゴリズムを実装する。

以下の直線検出の例を参照:

using namespace cv;
using namespace std;
int main(int argc, char** argv)
{
Mat src, dst, color_dst;
if( argc != 2 || !(src=imread(argv[1], IMREAD_GRAYSCALE)).data)
return -1;
Canny( src, dst, 50, 200, 3 );
cvtColor( dst, color_dst, COLOR_GRAY2BGR );
vector<Vec4i> lines;
HoughLinesP( dst, lines, 1, CV_PI/180, 80, 30, 10 );
for( size_t i = 0; i < lines.size(); i++ )
{
line( color_dst, Point(lines[i][0], lines[i][1]),
Point( lines[i][2], lines[i][3]), Scalar(0,0,255), 3, 8 );
}
namedWindow( "Source", 1 );
imshow( "Source", src );
namedWindow( "Detected Lines", 1 );
imshow( "Detected Lines", color_dst );
waitKey(0);
return 0;
}
#define CV_PI
Definition cvdef.h:386
void line(InputOutputArray img, Point pt1, Point pt2, const Scalar &color, int thickness=1, int lineType=LINE_8, int shift=0)
Draws a line segment connecting two points.
void Canny(InputArray image, OutputArray edges, double threshold1, double threshold2, int apertureSize=3, bool L2gradient=false)
Finds edges in an image using the Canny algorithm canny86 .
void HoughLinesP(InputArray image, OutputArray lines, double rho, double theta, int threshold, double minLineLength=0, double maxLineGap=0)
Finds line segments in a binary image using the probabilistic Hough transform.

これは関数の引数を調整するために用いたサンプル画像である:

image

そしてこれは、確率的ハフ変換の場合における上記プログラムの出力である:

image
引数
image8ビット、シングルチャンネルの2値入力画像。この画像は関数によって変更されることがある。
lines直線の出力ベクトル。各直線は4要素のベクトル \((x_1, y_1, x_2, y_2)\) で表現され、\((x_1,y_1)\) と \((x_2, y_2)\) は検出された各線分の端点である。
rhoアキュムレータの距離解像度(ピクセル単位)。
thetaアキュムレータの角度解像度(ラジアン単位)。
thresholdアキュムレータのしきい値引数。十分な票数 ( \(>\texttt{threshold}\) ) を得た直線のみが返される。
minLineLength直線の最小長。これより短い線分は棄却される。
maxLineGap同一直線上の点を連結するために許容される、点間の最大ギャップ。
参照
LineSegmentDetector

◆ HoughLinesPointSet()

void cv::HoughLinesPointSet ( InputArray point,
OutputArray lines,
int lines_max,
int threshold,
double min_rho,
double max_rho,
double rho_step,
double min_theta,
double max_theta,
double theta_step )
Python:
cv.HoughLinesPointSet(point, lines_max, threshold, min_rho, max_rho, rho_step, min_theta, max_theta, theta_step[, lines]) -> lines

#include <opencv2/imgproc.hpp>

標準的なハフ変換を用いて、点の集合から直線を検出する。

この関数は、ハフ変換の改良版を用いて点の集合から直線を検出する。

#include <opencv2/core.hpp>
using namespace cv;
using namespace std;
int main()
{
Mat lines;
vector<Vec3d> line3d;
vector<Point2f> point;
const static float Points[20][2] = {
{ 0.0f, 369.0f }, { 10.0f, 364.0f }, { 20.0f, 358.0f }, { 30.0f, 352.0f },
{ 40.0f, 346.0f }, { 50.0f, 341.0f }, { 60.0f, 335.0f }, { 70.0f, 329.0f },
{ 80.0f, 323.0f }, { 90.0f, 318.0f }, { 100.0f, 312.0f }, { 110.0f, 306.0f },
{ 120.0f, 300.0f }, { 130.0f, 295.0f }, { 140.0f, 289.0f }, { 150.0f, 284.0f },
{ 160.0f, 277.0f }, { 170.0f, 271.0f }, { 180.0f, 266.0f }, { 190.0f, 260.0f }
};
for (int i = 0; i < 20; i++)
{
point.push_back(Point2f(Points[i][0],Points[i][1]));
}
double rhoMin = 0.0f, rhoMax = 360.0f, rhoStep = 1;
double thetaMin = 0.0f, thetaMax = CV_PI / 2.0f, thetaStep = CV_PI / 180.0f;
HoughLinesPointSet(point, lines, 20, 1,
rhoMin, rhoMax, rhoStep,
thetaMin, thetaMax, thetaStep);
lines.copyTo(line3d);
printf("votes:%d, rho:%.7f, theta:%.7f\n",(int)line3d.at(0).val[0], line3d.at(0).val[1], line3d.at(0).val[2]);
}
void copyTo(OutputArray m) const
Copies the matrix to another one.
void HoughLinesPointSet(InputArray point, OutputArray lines, int lines_max, int threshold, double min_rho, double max_rho, double rho_step, double min_theta, double max_theta, double theta_step)
Finds lines in a set of points using the standard Hough transform.
引数
point点の入力ベクトル。各ベクトルは Point のベクトル \((x,y)\) として符号化されていなければならない。型は CV_32FC2 または CV_32SC2 でなければならない。
lines検出された直線の出力ベクトル。各ベクトルは vector<Vec3d> として \((votes, rho, theta)\) で符号化される。'votes' の値が大きいほど、そのHough直線の信頼性が高い。
lines_maxHough直線の最大数。
thresholdアキュムレータのしきい値引数。十分な票数 ( \(>\texttt{threshold}\) ) を得た直線のみが返される。
min_rhoアキュムレータの \(\rho\) の最小値(注: \(\rho\) は負になり得る。絶対値 \(|\rho|\) は直線から原点までの距離である)。
max_rhoアキュムレータの \(\rho\) の最大値。
rho_stepアキュムレータの距離分解能。
min_thetaアキュムレータの最小角度値(ラジアン)。
max_thetaアキュムレータの角度値の上限(ラジアン)。実際の最大角度は、パラメータ min_theta と theta_step によっては max_theta よりわずかに小さくなる場合がある。
theta_stepアキュムレータの角度解像度(ラジアン単位)。

◆ preCornerDetect()

void cv::preCornerDetect ( InputArray src,
OutputArray dst,
int ksize,
int borderType = BORDER_DEFAULT )
Python:
cv.preCornerDetect(src, ksize[, dst[, borderType]]) -> dst

#include <opencv2/imgproc.hpp>

コーナー検出のための特徴マップを計算する。

この関数は、ソース画像の複雑な空間微分に基づく関数を計算する

\[\texttt{dst} = (D_x \texttt{src} )^2 \cdot D_{yy} \texttt{src} + (D_y \texttt{src} )^2 \cdot D_{xx} \texttt{src} - 2 D_x \texttt{src} \cdot D_y \texttt{src} \cdot D_{xy} \texttt{src}\]

ここで \(D_x\), \(D_y\) は1次の画像微分、\(D_{xx}\), \(D_{yy}\) は2次の画像微分、\(D_{xy}\) は混合微分である。

コーナーは、以下に示すように、関数の局所最大値として求めることができる:

Mat corners, dilated_corners;
preCornerDetect(image, corners, 3);
// dilation with 3x3 rectangular structuring element
dilate(corners, dilated_corners, Mat(), 1);
Mat corner_mask = corners == dilated_corners;
void preCornerDetect(InputArray src, OutputArray dst, int ksize, int borderType=BORDER_DEFAULT)
Calculates a feature map for corner detection.
void dilate(InputArray src, OutputArray dst, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar &borderValue=morphologyDefaultBorderValue())
Dilates an image by using a specific structuring element.
引数
src入力のシングルチャンネル8ビットまたは浮動小数点画像。
dst型 CV_32F で src と同じサイズを持つ出力画像。
ksizeSobel の開口サイズ。
borderTypeピクセルの外挿方法。BorderTypes を参照。BORDER_WRAP はサポートされていない。