getDerivKernels
OpenCV が何を使用しているかを実際に確認したい場合は、Sobel フィルターのカーネル係数を決定するために使用できます。あなたがする必要があるのは、あなたが望む方向とあなたが望むマスクのサイズを指定することです. そのため、カーネルのサイズごとに 2 つの方向があるため、これを 4 回呼び出す必要があります。
ただし、返されるのは、を介して分離可能な 2D フィルタリングを実行するために使用できるソーベル フィルターを表す、水平、 x
、垂直 、 1D カーネルです。カーネル自体を実際に見たい場合は、 から返されるとカーネルの間の外積を取るだけです。y
sepFilter2D
x
y
getDerivKernels
Python の OpenCV インターフェイスを使用して 5 x 5 x
、y
および 7 x 7x
とy
カーネルを表示する簡単な例を次に示します。
In [1]: import numpy as np
In [2]: import cv2
In [3]: sobel5x = cv2.getDerivKernels(1, 0, 5)
In [4]: np.outer(sobel5x[0], sobel5x[1])
Out[4]:
array([[ -1., -4., -6., -4., -1.],
[ -2., -8., -12., -8., -2.],
[ 0., 0., 0., 0., 0.],
[ 2., 8., 12., 8., 2.],
[ 1., 4., 6., 4., 1.]], dtype=float32)
In [5]: sobel5y = cv2.getDerivKernels(0, 1, 5)
In [6]: np.outer(sobel5y[0], sobel5y[1])
Out[6]:
array([[ -1., -2., 0., 2., 1.],
[ -4., -8., 0., 8., 4.],
[ -6., -12., 0., 12., 6.],
[ -4., -8., 0., 8., 4.],
[ -1., -2., 0., 2., 1.]], dtype=float32)
In [7]: sobel7x = cv2.getDerivKernels(1, 0, 7)
In [8]: np.outer(sobel7x[0], sobel7x[1])
Out[8]:
array([[ -1., -6., -15., -20., -15., -6., -1.],
[ -4., -24., -60., -80., -60., -24., -4.],
[ -5., -30., -75., -100., -75., -30., -5.],
[ 0., 0., 0., 0., 0., 0., 0.],
[ 5., 30., 75., 100., 75., 30., 5.],
[ 4., 24., 60., 80., 60., 24., 4.],
[ 1., 6., 15., 20., 15., 6., 1.]], dtype=float32)
In [9]: sobel7y = cv2.getDerivKernels(0, 1, 7)
In [10]: np.outer(sobel7y[0], sobel7y[1])
Out[10]:
array([[ -1., -4., -5., 0., 5., 4., 1.],
[ -6., -24., -30., 0., 30., 24., 6.],
[ -15., -60., -75., 0., 75., 60., 15.],
[ -20., -80., -100., 0., 100., 80., 20.],
[ -15., -60., -75., 0., 75., 60., 15.],
[ -6., -24., -30., 0., 30., 24., 6.],
[ -1., -4., -5., 0., 5., 4., 1.]], dtype=float32)
カーネルは正規化されていないことに注意してください。これらをフィルタリングに使用する場合は、おそらくカーネルを正規化する必要があります。getDerivKernels
マスクを正規化できるフラグがあります。
また、特定のサイズの 1 つのマスクが別のマスクの転置であることに注意してください。これは、特定の方向のエッジを検出する場合に意味があります。
完全を期すために、上記の Python コードの C++ バージョンを次に示します。コードをコンパイルするには、これをファイルに配置します...呼び出してtest.cpp
から、ターミナルでこれを実行します。
g++ -Wall -g -o test test.cpp `pkg-config --cflags --libs opencv`
コンパイルしたら、 を使用してプログラムを実行し./test
ます。
#include <cv.h>
using namespace std;
using namespace cv;
int main() {
// For the kernels
Mat sobelX, sobelY;
// 5 x 5 - x direction
getDerivKernels(sobelX, sobelY, 1, 0, 5, false, CV_32F);
cout << "sobel5x = " << endl << " " << sobelX*sobelY.t() << endl << endl;
// 5 x 5 - y direction
getDerivKernels(sobelX, sobelY, 0, 1, 5, false, CV_32F);
cout << "sobel5y = " << endl << " " << sobelX*sobelY.t() << endl << endl;
// 7 x 7 - x direction
getDerivKernels(sobelX, sobelY, 1, 0, 7, false, CV_32F);
cout << "sobel7x = " << endl << " " << sobelX*sobelY.t() << endl << endl;
// 7 x 7 - y direction
getDerivKernels(sobelX, sobelY, 0, 1, 7, false, CV_32F);
cout << "sobel7y = " << endl << " " << sobelX*sobelY.t() << endl << endl;
return 0;
}
x
とy
カーネルはどちらも列ベクトルであるため、y
ベクトルを転置して、外積を計算する行ベクトルになるようにする必要があることに注意してください。