1. 형태
형태학(Morphology)은 이미지의 형태적 특성을 다루는 일련의 이미지 처리 기술을 말합니다 .
- 형태학의 기본 아이디어는 추가 이미지 분석 및 대상 인식을 위해 특수 구조 요소(본질적으로 컨볼루션 커널)를 사용하여 입력 이미지에서 해당 모양이나 특징을 측정하거나 추출하는 것입니다.
- 이러한 처리 방법은 기본적으로 바이너리 이미지 , 즉 흑백 이미지를 처리합니다.
- 컨볼루션 커널은 이미지 처리의 효과를 결정합니다.
형태학에서 일반적으로 사용되는 기본 연산은 다음과 같습니다.
- 팽창 및 부식
- 열림 작업
- 닫힘 작업
- 모자
- 검은 모자
1.1 이미지의 전역 이진화
이진화: 이미지의 각 픽셀을 0, 255와 같은 두 값으로 변환합니다.
0 및 255: 0은 검정색, 255는 흰색
01: 0은 검은색, 1은 흰색
- 임계값(src, thresh, maxval, 유형[, dst])
- src는 회색조 이미지인 것이 바람직합니다.
- thresh : 임계값
- maxval : 최대값, 최대값은 반드시 255일 필요는 없음
- 유형: 동작 유형 일반적인 동작 유형은 다음과 같습니다.
import cv2
import numpy as np
img = cv2.imread('./dog.jpeg')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
# 返回两个结果, 一个是阈值, 另一个是处理后的图片
ret, dst = cv2.threshold(gray, 80, 255, cv2.THRESH_BINARY)
cv2.imshow('dog', np.hstack((gray, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.2 적응형 임계값 이진화
이전 부분에서는 전체 이미지의 임계값과 동일한 숫자를 사용하여 전역 임계값을 사용했습니다 . 이 방법은 모든 상황에 적합하지는 않습니다. 특히 동일한 이미지의 서로 다른 부분의 밝기가 다른 경우에는 더욱 그렇습니다. 이 경우 적응형 임계값을 사용해야 합니다 . 이때의 임계값은 이미지의 작은 영역 각각을 기준으로 해당 임계값을 계산하는 것입니다. 따라서 동일한 이미지의 서로 다른 영역에서 서로 다른 임계값이 사용되므로 밝기가 다를 때 더 나은 결과를 얻을 수 있습니다.
adaptiveThreshold(src, maxValue,adaptiveMethod, ThresholdType, blockSize, C, dst=None)**
이 메서드에서는 6개의 매개변수를 지정해야 하며 하나의 값만 반환합니다.
• **적응 방법** - 임계값을 계산하는 데 사용되는 방법을 지정합니다.
– **cv2.ADPTIVE_THRESH_MEAN_C**: 인접 영역의 평균값에서 임계값을 가져옵니다.
– **cv2.ADPTIVE_THRESH_GAUSSIAN_C**: 인접 영역의 가중치 합에서 임계값을 가져오며, 가중치는 가우시안 윈도우입니다.
• **블록 크기** - 인접 크기(임계값을 계산하는 데 사용되는 영역의 크기).
• **C** - 이는 상수이며 임계값은 평균 또는 가중 평균에서 이 상수를 뺀 값과 같습니다.
# 因为光线问题, 全局二值化导致有部分地方看不见了.这时就需要自适应阈值二值化了.
import cv2
import numpy as np
img = cv2.imread('./math.png')
cv2.namedWindow('img', cv2.WINDOW_NORMAL)
cv2.resizeWindow('img', 1920, 1080)
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
# 自适应阈值二值化只返回一个值, 即二值化后的结果
dst = cv2.adaptiveThreshold(gray, 255, cv2.ADAPTIVE_THRESH_GAUSSIAN_C, cv2.THRESH_BINARY_INV, 3, 0)
cv2.imshow('img', np.hstack((gray, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.3 부식 작업
부식 작업 역시 컨볼루션 커널을 사용하여 이미지를 스캔하지만 부식 작업의 컨볼루션 커널 은 일반적으로 1입니다 . 컨볼루션 커널의 모든 픽셀이 흰색이면 앵커 포인트도 흰색입니다.
- 대부분의 경우 부식 작업은 모두 1의 컨볼루션 커널을 사용합니다.
- 침식(src, 커널[, dst[, 앵커[, 반복[, borderType[, borderValue]]]]])
- iterations는 부식 작업의 반복 횟수로, 횟수가 클수록 부식 작업이 더 많이 수행되며 부식 효과가 더욱 뚜렷해집니다.
import cv2
import numpy as np
img = cv2.imread('./msb.png')
kernel = np.ones((3, 3), np.uint8)
dst = cv2.erode(img, kernel, iterations=2)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.4 형태학적 컨벌루션 커널 획득
- opencv는 컨볼루션 커널을 얻기 위한 API를 제공하므로 컨볼루션 커널을 수동으로 생성할 필요가 없습니다.
- getStructuringElement(shape, ksize[, 앵커])
- Shape는 컨볼루션 커널의 모양을 의미하며, 길이와 너비를 의미하는 것이 아니라 컨볼루션 커널의 1이 이루는 모양을 의미함을 의미함
- MORPH_RECT 컨볼루션 커널의 1은 직사각형으로, 일반적으로 사용됩니다.
- MORPH_ELLIPSE 타원
- MORPH_CROSS 십자형
import cv2
import numpy as np
img = cv2.imread('./j.png')
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
dst = cv2.erode(img, kernel, iterations=2)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.5 확장작전
팽창(Dilation)은 침식(Erosion)의 반대 연산으로 컨볼루션 커널의 앵커 포인트가 0이 아닌 값이 보장되는 한 주변 값은 0이든 0이든 상관없이 0이 아닌 값이 되는 것이 기본 원리이다. 0이 아닌 값.
- 확장(img, 커널, 반복=1)
import cv2
import numpy as np
img = cv2.imread('./j.png')
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
dst = cv2.dilate(img, kernel, iterations=2)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.6 오픈 동작
열기 및 닫기 작업은 모두 침식 및 팽창의 기본 응용 프로그램입니다.
- 열기 연산 = 침식 + 확장
- morphologyEx(img, MORPH_OPEN, 커널)
- MORPH_OPEN은 형태학적 열기 연산을 나타냅니다.
- kernel 노이즈 포인트가 많으면 큰 커널이 선택되고, 노이즈 포인트가 작으면 작은 커널이 선택됩니다.
import cv2
import numpy as np
img = cv2.imread('./dotj.png')
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5))
# 腐蚀
# dst = cv2.erode(img, kernel, iterations=2)
# # 膨胀
# dst = cv2.dilate(dst, kernel, iterations=2)
# 直接调用opencv提供的开运算api
dst = cv2.morphologyEx(img, cv2.MORPH_OPEN, kernel, iterations=2)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.7 폐쇄된 운영
- 닫힌 연산 = 팽창 + 침식
import cv2
import numpy as np
img = cv2.imread('./dotinj.png')
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5))
dst = cv2.morphologyEx(img, cv2.MORPH_CLOSE, kernel, iterations=2)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.8 형태적 구배
- 그라데이션 = 원본 이미지 - 부식
- 부식 후 원본 이미지의 가장자리가 작아집니다 원본 이미지 - 부식으로 인해 부식된 부분, 즉 가장자리가 생길 수 있습니다.
import cv2
import numpy as np
img = cv2.imread('./j.png')
# 注意调节kernel大小以获得更清晰的边缘
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
dst = cv2.morphologyEx(img, cv2.MORPH_GRADIENT, kernel, iterations=1)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.9 모자 작동
- 모자 = 원본 이미지 - Open 작업
- Open 작업의 효과는 이미지 외부의 노이즈를 제거하는 것입니다. 원본 이미지 - Open 작업을 수행하면 노이즈가 제거됩니다.
import cv2
import numpy as np
img = cv2.imread('./tophat.png')
# 注意调整kernel以保留小图形
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (19, 19))
dst = cv2.morphologyEx(img, cv2.MORPH_TOPHAT, kernel, iterations=1)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()
1.10 블랙햇 운용
- 검은 모자 = 원본 이미지 - 닫힌 작업
- 닫힌 작업은 그래픽 내부 노이즈를 제거할 수 있으며 원본 이미지의 결과 - 닫힌 작업은 그래픽 내부의 노이즈입니다.
import cv2
import numpy as np
img = cv2.imread('./dotinj.png')
# 注意调节kernel大小以获得更清晰的边缘
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (7, 7))
dst = cv2.morphologyEx(img, cv2.MORPH_BLACKHAT, kernel, iterations=1)
cv2.imshow('img', np.hstack((img, dst)))
cv2.waitKey(0)
cv2.destroyAllWindows()