Numpy로 이미지 마스크를 만들 때 유형에주의하십시오.

4252 단어 파이썬OpenCVnumpy

하고 싶은 일



화상이나 동영상의 일부 이외를 검게 채워 자르고 싶은 경우, 화상의 마스크를 작성해, 그것을 중첩하는 것으로 실현한다.

원본 이미지

마스크된 이미지


실패



Numpy를 사용하여 검정색으로 칠하고 싶은 범위는 0, 자르고 싶은 범위는 1로 하는 마스크를 작성.
행렬의 각 요소를 걸면 마스크할 수 있다고 생각하면, 생각했던 것과 다른 출력이 되었다.
h_img, w_img = img.shape[:2]
mask = np.zeros((h_img, w_img, 3))
radius = int(h_img / 2)
center = radius
cv2.circle(mask, (center, center), radius, (1, 1, 1), thickness=-1, shift=0)
masked_img = img * mask

Numpy로 만든 마스크 (mask)


마스크된 이미지(masked_img)


원인과 해결책



Numpy 로 행렬을 정의할 때, dtype 를 지정하지 않으면 디폴트에서는 float64 형이 된다. 반면에 opencv의 imread로 읽은 이미지는 휘도에 따라 CV_8U, CV_16F 및 CV_32F로 읽습니다 (일반적으로 CV_8U). CV_8U라면 Numpy의 데이터형에서는 np.uint8에 대응하고 있다.
즉, 실패한 예에서는 CV_8U 의 화상에, float64 형의 마스크를 걸고 있다.

Numpy 로 행렬을 정의할 때에, 형태를 np.uint8 로 지정해 준다.
할 수 있었다.
mask = np.zeros((h_img, w_img, 3), dtype=np.uint8) # 型を uint8 に指定

마스크된 이미지


마스크를 이미지로 표시해 보면, 새까만.


소감



데이터형의 불일치라고 하는 초보적인 실수이지만, 최근 python만 사용하고 있어, 형태를 의식하는 기회가 줄어들고 있는 탓인지, 눈치채는데 시간이 걸렸다.
원래, np.zeros 로 정의하지 않고, np.zeros_like 를 사용해 image 의 형태 포함해 행렬 정의하면 좋았다.

좋은 웹페이지 즐겨찾기