OpenCV 4.0
설치를해보자 일단은 C++ 기반으로
우분투에 GCC 설치 후
OpenCV 모듈
- 기본적으로 lib 와 dll로 구성
- 필요한 모듈을 선택적으로 가져오거나 world를 추가해서 한번에 가져옴
- 현재 추가모듈형태로 개발되고 있으며 opencv_contrib 저장소에 배포중
- 레퍼런스 는 여기 https://docs.opencv.org/
주요 모듈
- core : 핵심 클래스와 연산 함수
- dnn : 신경망
- featured2d : 2차원 피쳐 기능들
- imgcodecs : 영상파일 입출력
- ml : 통계적 머신러닝 알고리즘
- highgui : 사용자 인터페이스
- imgproc : 필터링 기하학적 변환, 색공간 변환
- objdetect : 객체 검출
- photo : 사진처리기능
- video : 옵티컬플로우, 배경차분 등 동영상 처리기술
- videoio : 동영상파일 입출력
- world : 여러가지 모듈을 포함하는 통합 모듈
- calib3d : 카메라 캘리브레이션
설치
리눅스에선 역시나 소스코드를받아서 컴파일해야하는 수고로움이… 그래도 한번하면 편할테니 ㅠㅠ
https://webnautes.tistory.com/1030
여기를 참고하엿다
수많은 패키지를 설치하라고 하는데
중간에오류나기싫으면 최대한 다 설치해주자…
컴파일 후 실행하면 설치가 되는데
라이브러리 연결이…
$(pkg-config opencv4 00libs –cflags)
를 사용하면되는데ㅐ
vscode에서 사용하려니 앞뒤로 ‘‘가 붙어서 못쓴다..
그냥 띄어쓰기마다 ““로 나눠서 넣어주니 됨…
사용함수
MAT
이미지를 저장할 행렬 클래스
- empty() : 행이나 열이 0이거나 데이터가 NULL이면 true 반환
namespace cv
가장 기본 클래스
이미지관련
- imread(filename, ImreadModes ) : 이미지 읽어오긔,
- 모드는 색상 채널방식이고 설정시 자동 변환, 참고로 칼라는 BGR
- ImreadModes 참고 (IMREAD_COLOR(BGR), INREAD_GRAYSCALE, IMREAD_UNCHANGED 등)
- imwrite(filename, mat, param) : 이미지 쓰기
- param은 std::vector형으로 플래그와 값을 쌍으로 순서대로 푸시
- imshow(windowname, mat) : 특정윈도우에 mat을 그려서 보여줌
- 해당 윈도우가 없을경우 AUTOSIZE로 새로만들어버림 (namedWindow 생략 가능)
윈도우관련
- namedWindow(windowname, flags) : 창에 이름넣어 만들기(이름으로 호출)
- 창의 속성 플래그는 WindowFlags 참고 (WINDOW_AUTOSIZE, WINDOW_NORMAL등)
- moveWindow(windowname, x, y) : x,y 픽셀만큼 이동
- resizeWindow(windowname, width, height) : 윈도우 사이즈조절
- distroyWindow(windowname) : 닫긔
- distroyAllWindows(): 다닫긔
기타
- int waitKey(int delay=0) : 일정시간 키입력을 기다림
- 사실 이 함수가 그리는 명령을 실행하기에 show 뒤에 꼭 써줘야함
- 키가 입력될시 해당하는 아스키코드 출력
- delay동안 입력이 없을시 -1 리턴
주요 클래스
- “재정의” 가 붙은 클래스는 _ 대신 2i, 2l, 2f, 2d 를 붙여 데이터형식을 정의 가능 (default : Point2i )
- Point_ : 점을 표시하는 데이터형 (재정의)
- ddot(Point_), cross(Point_), inside(Rect_)) : 내적, 외적, 내부 판단
- Size_ : 말그대로 사이즈 (재정의)
- area() : 두개의 곱
- empty() : 빈 자료형
- Rect_ : 사각형 자료 (재정의)
- tl(), br() : 탑레프트, 바텀라이트
- size(), area() : 사이즈, 넓이
- empty(), contains(Point_) : 비었는지 포함하는지
- RotatedRect(Point_, Size_, angle) : 회전된 사각형
- points() : 네 꼭지점 자료 (이게 왜 public?)
- boundingRect(), boundingRect2f() : 회전된것의 꼭지점을 포함하는 최소 사각형
- Range : 시작점과 끝점
- size() : end - start
- static all() : INT_MIN, INT_MAX 반환
- String : C의 std::string과 동일
자료형
uchar, CV_8U : unsigned char
schar, CV_8S : signed char
ushort, CV_16U : unsigned short
short, CV_16S : signed short
int, CV_32S : int
CV_32F : float
CV_64F : double
CV_16F : float16
- 뒤에 C? 를 붙임으로 채널수 조정 가능 ( CV_32FC3)
Mat 생성방법
- Mat matName (row, col, type, const T& s)
- 가장 기본적인 생성방식
- 기본적으로 초기화가안되므로 s초기화값을 꼭 쓰는것을 추천
- row, col 대신 size 클래스도 사용 가능
- void* data 를 넣어 외부 데이터로 생성도 가능
- 소멸시 메모리 자동 해제가 안되므로 직접 해제해야함
- eye(), ones(), zeros() : 특정 형태로 초기화
- MAT_ (Mat을 상속받은 클래스 템플릿) 를 이용한 방법
```
MAT_ mat5_(2,3); // 선언
mat5_ << 1,2,3,4,5,6>>; // 값 할당
Mat mat5 = mat5_; // 매트릭스로 변환
MAT mat6 = MAT_({2,3}, {1,2,3,4,5,6}) // 4.0부터 가능한 초기화법
MAT mat7;
mat7.create(256, 256, CV_8UC3); // 비어있을시엔 생성, 기존의 행렬과 크기와 타입이 같을경우 아무것도안함, 다를경우 새로운 행렬 생성
mat7.setTo(5) // create는 초기화 기능이 없음
// 행렬 복사
MAT mat8 = mat7 ;
MAT mat9;
mat9 = mat7; // 복사생성자 및 대입연산자는 얕은복사를 수행
MAT mat8 = mat7.clone();
mat9 = mat7.copyTo(); // 깊은 복사용 생성자 및 깊은복사
## 행렬 부분추출
- 모든 추출은 얕은 복사이므로 깊은복사시 .clone() 필요
MAT img1 = imrear(“cat.jpg”);
img2 = img1(RECT(10,10,20,30)); // 원본 이미지의 부분추출 (얕은복사)
img2 = img1.rowRange(1,10); // 1행부터 10행까지 추출
img2 = imt1.colRange(5,10); // 1열부터 10열까지 추출
img2 = img1.row(1) // 1행추출
img2 = img1.col(1) // 1열추출
float a = img1.at(5, 3) // 5행 3열 픽셀의 데이터 추출
float* = img1.ptr(3) // 3행의 첫번째 원소의 주소값 반환
for ( auto it = mat1.begin(); it !=mat.end; it++)
(*it)++;
Mat img1 = imread(“cat.jpg”);
img1.channels(); // 채널수 반환
img1.depth(); // 깊이 반환? CV_8U 등. 이게 왜 깊이일까요?
img1.elemSize() // 한개의 원소가 차지하는 메모리크기를 바이트단위로 반환
img1.elemSize1() // 한 채널에서 원소가 차지하는 메모리크기 바이트단위로 반환
float data[] = {1,1,2,3};
Mat mat1(2,2, CV_32FC1, data); // 데이터로부터 mat1 생성
Mat mat2 = mat1.inv(); // Inverse 역행렬
Mat mat3 = mat1.t(); // Transpose 전치
Mat mat4 = mat1 + mat2; // 사칙연산 가능, * 은 원소별 연산
Mat mat5 = mat1.mul(mat2); // Matrics multiply 행렬곱
Mat mat = Mat_({2,2},{1,3,2,4});
Mat mat2;
mat.convertTo(mat2, CV_32FC1); // 32비트 float형으로 변환하여 mat2에 저장
mat3 = mat.reshape(0,1) // 형상의 변환, 채널과 행을 변화, 주의할 점은 형태변형이지만 참조이므로 원래 자료가 변할 수 있음
mat4 = mat.resize(3, 1) // 행수 변경 가능. 3행으로변경 후 빈값은 1로 초기화
mat_1 = Mat_({1,2},{3,4});
mat.push_back(mat_1r); // 열단위로 푸쉬가 이루어지므로 행이 같아야 입력 가능
mat.pop_back(2); // 아래부터 2행 제거, 팝이있는거보니 스택형인듯
```
벡터와 스칼라
- Vector
- Point와 마찬가지로 대부분이 재정의되어있음
- Vec2b : 바이트형(2,3,4가 있음)
- Vec2s : 숏형(2,3,4)
- Vec2w : 언사인드 숏형(2,3,4)
- Vec2i : 정수형(2,3,4,6,8)
- Vec2f : 플롯형(2,3,4,6)
- Vec2d : 더블형(2,3,4,6))
- 오퍼레이터 [] 가 정의되어있어 원소에 쉽게 접근 가능
- 사칙연산등 여러가지 함수가 정의 되어있음
- Scalar
- 4개의 원소를 가진 벡터( 자주사용되는 벡터라 따로 만든듯한 느낌)
- Scalar_ 식으로 재정의가 필요함 (Scalar 기본은 더블형)
- 색상픽셀 표현에 주로 사용
- 벡터와 마찬가지로 []가 정의되어있어서 자주 사용됨
- 그레이스케일은 1채널만, RGB는 3채널, 투명도가 포함되면 4채널 ( 안쓰는채널은 0값을 가짐)
- ㅡMat, Vec 등의 입력과 출력용으로 사용되는 인터페이스
- 여러가지 형태의 입력을 받고싶을때 하나로 통일 가능
- 절대로 직접 변수를 생성하면 안됨 (그러면 못하게 해놓든가)