앎을 경계하기

Machine Learning/For CV

3. 밝기 변환과 공간 필터링(2)

양갱맨 2020. 11. 5. 11:35

3.2.4 구간 선형 변환 함수

앞서 보았던 영상 네거티브, 로그 변환, 감마 변환에 대해 보완된 방법이 구간 선형 함수를 사용하는 것이다.

  • 장점 : 구간 함수들의 형태가 임의로 복잡해질 수 있다.
  • 단점 : 함수를 규정하기 위한 사용자 입력이 훨씬 더 많이 필요하다.
  1. Contrast Stretching

    가장 간단한 구간 선형 함수 중 하나.

    낮은 콘트라스트 원인은 나쁜 조명, 영상화 센서의 좁은 동적 범위, 영상 획득 시 잘못된 조리개 설정 등이다. 콘트라스트 스트레칭은 밝기 레벨의 범위를 넓혀 매체의 전체 밝기 범위를 사용하게 하는 것이다.

    (r1,s1)=(rmin,0),(r2,s2)=(rmax,L1)(r_1, s_1)=(r_{\min},0), (r_2, s_2)=(r_{\max},L-1)으로 레벨 범위를 [0, L-1]로 선형적으로 스트레칭 할 수 있다.

    #Contrast Stretching
    img_path = '/content/low_lena.png'
    img = cv2.imread(img_path)
    img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    cv2_imshow(img)
    
    '''
    level range = [0,L-1]
    (r1,s1)=(min(r),0)
    (r2,s2)=(max(r),L-1)
    '''
    
    def Stretch_Contrast(img, L):
        res = np.array(img)
        min_ = np.min(img)
        max_ = np.max(img)
    
        for x in range(img.shape[0]):
            for y in range(img.shape[1]):
                res[x][y] = ((img[x][y]-min_)/(max_-min_))*(L-1)
        return res
    res = Stretch_Contrast(img, 256)
    cv2_imshow(res)
    contrast stretching
    low contrast image
    plt.hist(img.flatten(),color='#FF000066')
    plt.hist(res.flatten(),color='#0000FF66')
    Red → low contrast, Blue → Contrast Stretching 레벨 범위가 넓어진 것을 볼 수 있다.
  1. Intensity-level slicing

    특정 밝기 범위를 강조하기 위한 프로세스로 대개 두 가지 방법을 기반으로 변형되었다.

    • 관심 영역에 드는 값들을 한 값으로 표시하고 나머지를 다른 값으로 표시하는 방법으로 결과적으로 이진 영상을 만든다.
    • 원하는 범위만 어둡거나 밝게 만들고 나머지는 그대로 둔다.
  1. Bit-Plane slicing

    각 비트에 대하여 0또는 1인지 검사하여 영상 형태로 만든 것으로 8비트 영상은 8개의 1비트 평면들로 구성된 것이다.

    영상을 비트 평면들로 분해하는 것은 영상에서의 각 비트의 상대적 중요성을 분석하는데 유용하다. n번째 비트를 십진수로 전환하여 복구하는데 사용할 수 있다. 주요 특징들은 복원되나 원래 이미지보다 단조로운 표현을 확인할 수 있다.

  1. 히스토그램 처리

    밝기 레벨의 범위가 [0, L-1]인 디지털 영상의 히스토그램은 이산 함수 h(rk)=nkh(r_k)=n_k 이다. rkr_k 는 k번째 밝기이고 nkn_k 는 밝기 r을 갖는 화소들의 수다.

    보통 히스토그램의 성분을 각각 영상 전체 화소 수로 나눠서 normalization 처리를 한다.

    p(rk)=nk/(MN)p(r_k)=n_k/(MN)

    MN : 이미지 전체 화소 수, p(rk)p(r_k) : 레벨 rkr_k 발생할 확률의 추정 값

    import cv2
    from google.colab.patches import cv2_imshow
    import numpy as np
    
    b_path = '/content/cat.jpg'
    w_path = '/content/catw.jpg'
    
    b = cv2.imread(b_path,0)
    w = cv2.imread(w_path,0)
    
    b = cv2.resize(b,(224,224))
    w = cv2.resize(w,(224,224))
    
    cv2_imshow(b)
    cv2_imshow(w)

    히스토그램을 확인해보면..

    import matplotlib.pyplot as plt
    
    plt.hist(b.ravel(), bins=256, range=[0,255],color='#ff00d3d2')
    plt.hist(w.ravel(), bins=256, range=[0,255],color='#00c467d2')

    어두운 영상(분홍)은 왼쪽으로 편향되어있고, 밝은 영상(초록)은 오른쪽에 편향되어있다.

    Contrast 값이 높은 영상은 히스토그램의 분산이 넓게 나타난다.

    #contrast 높이기(히스토그램 평활화)
    high_b = cv2.equalizeHist(b)
    cv2_imshow(b)
    cv2_imshow(np.concatenate((b,high_b),axis=1))
    
    high_w = cv2.equalizeHist(w)
    cv2_imshow(w)
    cv2_imshow(high_w)

    원본과 히스토그램 평활화 적용한 이미지의 히스토그램 비교

    plt.hist(b.ravel(), bins=256, range=[0,255],color='#ff00d3d2')
    plt.hist(high_b.ravel(), bins=256, range=[0,255],color='#0000ff66')
    plt.hist(w.ravel(), bins=256, range=[0,255],color='#00c467d2')
    plt.hist(high_w.ravel(), bins=256, range=[0,255],color='#ff000066')

    파란색과 빨간색(어두운 또는 밝은 영상의 콘트라스트를 높인) 히스토그램 분포가 넓게 표현된 것을 확인하였다.

    히스토그램은 소프트웨어에서 계산하기 쉽고, 하드웨어 구현에도 알맞다고 한다. 히스토그램의 수평축은 밝기 레벨이고 수직은 그 밝기를 갖는 픽셀 수다.

4.1 히스토그램 평활화

영상의 대조를 높이면 히스토그램의 분산이 넓게 표현된다는 것을 위에서 확인했다.

히스토그램 평활화는 어떻게 수행되는 것일까?

사전에 밝기값이 연속적이고 처리될 영상의 밝기가 r이라고 하자. r의 범위 : [0, L-1], r=0 black, r=L-1 white 라고 한다.

이때 r에 대해 다음과 같은 밝기 매핑에 집중한다.

s=T(r)0rL1s=T(r)\\0\leq r \leq L-1

위 식은 밝기 레벨 r을 갖는 입력 영상의 모든 화소에 대해 출력 밝기 레벨 s를 만든다.

그리고 몇 가지 가정을 한다.

(a) T(r)T(r)0rL10 \leq r \leq L-1구간의 단조 증가 함수(monotonically increasing function)이다.

(b) 0rL10 \leq r \leq L-1에 대해 0T(r)L10 \leq T(r) \leq L-1이다.

일부 공식에서 다음의 역을 사용한다.

r=T1(s)0sL1r = T^{-1}(s)\\0 \leq s \leq L-1

역을 사용하는 경우 (a)조건을 (a')으로 바꾼다.

(a') T(r)T(r)0rL10 \leq r \leq L-1 구간의 엄밀 단조 증가 함수이다.

  • 단조증가란? 함수가 감소하는 부분없이 계속 증가하는 형태이다.

단조증가해야한다는 조건은 (a)의 출력값이 입력값보다 작지 않음을 보장한다.

(b) 조건은 출력 밝기 범위가 입력 밝기 범위와 같음을 보장한다.

(a')는 (a), (b) 만 충족했을때 발생할 수 있는 비유일 역변환 문제를 해결하기 위해 s에서 r로 복원시 1:1 매핑 되는 것을 보장한다.

예를 들어, 아래 그림과 같이 여러 입력에 대해 동일 출력값이 나오는 경우, 역함수를 사용해 출력을 통해 입력을 구하려면 1:1 매핑이 불가능하여 값의 범위가 나오게 된다. 이것은 찾고자하는 r을 찾기 어렵게 한다. 이것을 (a)의 단조 증가 함수 조건 대신 엄밀 단조 증가 함수로 바꿔서 1:1 매핑이 가능하도록 한다.

이것은 이론적인 조건이고 실제로는 nearest neighbor 방식을 사용하여 최근접 정수로 비유일 역변환 문제를 처리한다.