OpenCV深い学習(2)-マット構造初期化など


主にマニュアルのこの部分に関する翻訳です.
Matオブジェクトを作成するには、1、create(nrow,ncols,type)関数、または類似のコンストラクション関数Mat(nrow,ncols,type[,fillValue])を使用すると、新しい指定されたサイズとフォーマットの配列が割り当てられます.typeの意味はcvCreateMat関数と同じです.例えばCV_8 UC 1は8ビットの単一チャネルの配列を作成することを意味し、CV_32 FC 2は2チャネルの浮動小数点数配列である.例:
//    7*7           1+3j;
cv::Mat M(7,7,CV_32FC2, Scalar(1,3));
//   M   100*60 15   8   ;
M.create(100,60,CV_8UC(15));

最初に説明したように、create()関数は、現在の配列サイズまたはタイプが指定したものと異なる場合にのみ新しい配列を割り当てます.2、1と同様に、多次元配列を作成することもできます.
//  100*100*100 8   
int sz[]={100,100,100};
cv::Mat bigCube(3, sz, CV_8U, Scalar::all(0));

コンストラクション関数の次元パラメータdimensions=1に渡されても、作成された配列は2次元配列、すなわちパラメータdims=2となり、関数は行列を複数行1列のみの行列と見なすのでMat::dimsは常に2以上(配列が空の場合は0);3、以下に示すように、複製コンストラクタまたは複製オペレータを使用する.説明したように、付与操作の計算複雑度はO(1)である、オブジェクトヘッダのコピーと参照カウントの増加(実際のコピーデータはない)を行うだけであるため、必要に応じて関数Matを用いることができる.clone()は、配列の完全なコピーを取得します.4、他のMat配列のために新しいヘッダを構築し、Mat配列は1行、1列、複数行、複数列、行列配列の矩形領域または対角線であり、これらの操作の複雑さもO(1)であり、新しいヘッダは同じデータを指すため、この特徴を使用して配列の一部を変更することができる.
//  5       3  
M.row(3)=M.row(3)+M.row(5)*3;
//  7     1 ,   M.col(1)=M.col(7)      ,        :
Mat M1 = M.col(1);
M.col(7).copyTo(M1);
//    320×240   
Mat img(Size(320,240), CV_8UC3);
//    ROI
Mat roi(img, Rect(10, 10, 100, 100));
// ROI        ,   img      。
roi=Scalar(0,255,0);


追加のメンバー:datastartとdataendのヘルプのため、locateROI()関数を使用してサブブロックのプライマリ配列内の相対位置を計算できます.
Mat A=Mat::eye(10,10, CV_32S);
//  A  [1,3),      ;
Mat B = A(Range::all(), Range::(1,3));
//  B  [5,9),  C  A 5-8 ,1-2 ;
Mat C = B(Range::(5,9),Range::all());
Size size;Point ofs;
C.locateROI(size, ofs);
//size (10,10),ofs(x=1,y=5)

必要に応じてclone()関数を使用して、析出したサブマトリクスをコピーできます.5、ユーザ外部データに対象ヘッダを割り当てる方法であって、(1)、OpenCVを用いて外部データを処理する(例えば、自己実現のDirectShowのフィルタやgstreamerの処理モジュールなど)、例えば
void process_video_frame(const unsigned char *pixels, int width, int height, int step)
{
	Mat img(height, width, CV_8UC3, pixels, step);//    height width  cols rows     ;
	GaussianBlur(img, img, Size(7,7), 1.5,1.5);
}

(2)、小さなマトリクスをすばやく初期化し、super-fastの要素取得速度を取得する.
double m[3][3] = {{a,b,c},{d,e,f},{g,h,i}};
Mat M = Mat(3,3, CV_64F, m).inv();

一般的ではないが非常に一般的なユーザ割付データの使用は、CvMatまたはIplImageからMatへの変換時に「partial yet very common cases of this..case」であるため、CvMatまたはIplImageを指すポインタと、データ複製の有無を示すフラグflagをパラメータとするMatコンストラクタがある.MatからCvMatまたはIplImageへの逆変換は、リロードされたオペレータMat::operator CvMat()およびMat::operator IplImage()によって行われ、データはコピーされません.
IplImage *img = cvLoadImage("greatewave.jpg",1);
Mat mtx(img); //IplImage*->Mat
CvMat oldmat = mtx; //Mat->CvMat
CV_Assert(oldmat.cols==img->width && oldmat.rows==img->height && oldmat.data.ptr==(uchar *)img->imageData && oldmat.step==img->widthStep);

6、MATLABスタイルのマトリクス初期化関数、zeros()、ones()、eys()、例えば//二重精度の単位マトリクスを作成し、Mに追加する;M += Mat::eye(M.rows, M.cols, CV_64F);
7、カンマ区切りで初期化;//作成3×3の二重精度単位アレイ;Mat M = (Mat_(3,3) << 1,0,0,0,1,0,0,0,1); この方法を使用して、適切なパラメータが与えられたMat_を呼び出すことができます.クラスのコンストラクション関数は、定数、変数、式などをカンマで区切った値を<<オペレータで入力できます.コンパイルエラーを回避するために追加されたカッコに注意してください.【これで基本的にMatマトリクスを作成する一般的な方法はすべて比較的に完全で、構造関数の中にいくつかの実用的なテンプレートで実現された構造関数があることを見て、パラメータはVec、Matxおよびvectorのです;8、テンプレートを使用する構造関数;
	const int dimss=40;
	vector<float> stl_vec;
	Vec<short, dimss> vecs;
	Matx<double, 30, 50> matxs;
	for (int i=0; i<dimss; ++i)
	{
		vecs[i] = i*3;
		stl_vec.push_back(i*10.f);
	}
	Mat vecMat(vecs);
	Mat matxMat(matxs);
	Mat stlvecMat(stl_vec,true);

この方法は主にベクトル表現をMatに変換するためのマトリクス表現の便利な処理であり,findContourを用いて得られた輪郭のようにベクトルの構造が重要であり,PointのvectorをMat処理に変換することができる.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------次にMat要素の入手方法をまとめます.