Head vs breakz

[인공지능] - One shot learning with Siamese Networks using keras - Harshall lamba - 1 본문

Head/인공지능

[인공지능] - One shot learning with Siamese Networks using keras - Harshall lamba - 1

headbreakz 2020. 2. 27. 15:12

One shot learning with Siamese Networks using keras - Harshall lamba

https://towardsdatascience.com/one-shot-learning-with-siamese-networks-using-keras-17f34e75bb3d

를 공부하기 위해 번역과 정리 하는 글입니다.

One shot learning with Siamese Networks using keras -1

소개

많은 양의 데이터를 수집하는데 어려움이 있기 떄문에, One shot learning을 통해 해결 하고자 한다.

Classification vs one shot learning

분류 모델의 경우 입력 이미지가 레이어들을 거쳐, 마지막으로 모든 클래스에 대한 확률 분포를 만들어 출력한다. 예를 들면 입력한 이미지를 고양이,개,말,코끼리로 분류하는 경우, 모든 입력이미지에 대해 4개 클래스(고양이,개,말,코끼리)에 속할 확률을 생선한다. 여기서 중요한 2가지 포인트는, 첫째 훈련 과정(모델 훈련)에서 수많은 이미지를 필요로 한다.그리고 2번째로는 4개의 이미지 클래스를 학습 시킬 경우, 이외의 클래스는 테스트를 할수 없다. 다른 클래스를 분류하고자 한다면, 다시 훈련을 시켜야 하므로 데이터수집과 재교육 비용이 높게 너무 높게 들어간다.

One shot 분류의 경우에는 각 클래스에 대해 하나의 데이터가 필요하다.

  • 사용 사례

직원 수가 10명인 곳에서 얼굴 인식 시스템을 구축하려고 할때, one shot learing을 이용할 경우, 입력한 이미지를 10명중 한명으로 직접적으로 분류하는 것이 아닌 이 네트워크는 사람의 추가 이미지를 가져와서 입력하여, 2개의 입력 이미지가 같은 사람에 속할 유사성 점수를 생성한다. 유사성 점수는 0과 1를 사용하는 sigmoid 함수를 사용한다.

이 네트워크는 직접적으로 이미지를 분류하는 것이 아닌, 2개의 입력 이미지와 유 사성에 대한 유사성 함수(similarity function)를 배운다

Applications

  • AI Guru Andrew Ng demonstrates how Baidu (the Chinese Search Giant)가 직원 얼굴 인식하는 방법 link

  • 데이터가 부족한 약물에 대해 one shot learning을 사용한 경우 blog

Dataset

 one-shot learning을 실습하기 위해 Omniglot Dataset을 사용하였다.Omniglot dataset은 1623 손으로 그려낸 50개의 다른 알파벳의 데이터이다. 모든 문자에 대해 서로 다른 사람이 그려낸 20개의 예제가 있고, 각각의 이미지는 105 x 105의 회색 이미지 이다

여기서 알파벳은 영어 문자를 나타내는 알파벳이 아닌, 문자의 집합을 알파벳이라 한다. 결국 총 1623개의 서로 다른 클래스가 있고, 각 클래스마다 20개의 이미지가 있다.

Data load

Data를 불러오는 과정은 본문을 참고, 여기서 사용하는 것은 images_background 폴더에 있는 30개의 알파벳과 images_evaluation 폴더에 있는 20개의 알파벳을 사용하였다.

x.shape
(964,20,105,105)

30개의 다른 알파벳에서 964개의 문자, 20개의 이미지, 105 x 105의 회색 이미지

y.shape
(19280,1)

총 이미지 19280개를 사용한다.

Mapping the problem to binary classification task

(Xi,Yi)를 가지고 있는 데이터 셋에서 어떻게 매핑 할 것인지 생각해보자. Xi는 입력,Yi는 출력을 나타낸다.

Xi = 이미지의 쌍

Yi= 1, 인 경우 두 이미지는 비슷한 문자를 가지고 있다.

Yi= 0, 인 경우 두 이미지는 다른 문자를 가지고 있다.

Siamese Network에 입력으로 넣기 위해 위와 같은 형식으로 두 이미지에 대한 값을 만들어야 한다. 위에서는 sanskrit 알파벳을 사용하여 보여주었지만, 실제로는 전체가 임의로 짝을 만들어 낸다.

  • 이미지 쌍과 값을 만들어 내는 코드
def get_batch(batch_size,s="train"):
    """
    Create batch of n pairs, half same class, half different class
    """
    if s == 'train':
        X = Xtrain
        categories = train_classes
    else:
        X = Xval
        categories = val_classes
    n_classes, n_examples, w, h = X.shape

    # randomly sample several classes to use in the batch
    categories = rng.choice(n_classes,size=(batch_size,),replace=False)

    # initialize 2 empty arrays for the input image batch
    pairs=[np.zeros((batch_size, h, w,1)) for i in range(2)]

    # initialize vector for the targets
    targets=np.zeros((batch_size,))

    # make one half of it '1's, so 2nd half of batch has same class
    targets[batch_size//2:] = 1
    for i in range(batch_size):
        category = categories[i]
        idx_1 = rng.randint(0, n_examples)
        pairs[0][i,:,:,:] = X[category, idx_1].reshape(w, h, 1)
        idx_2 = rng.randint(0, n_examples)

        # pick images of same class for 1st half, different for 2nd
        if i >= batch_size // 2:
            category_2 = category  
        else: 
            # add a random number to the category modulo n classes to ensure 2nd image has a different category
            category_2 = (category + rng.randint(1,n_classes)) % n_classes

        pairs[1][i,:,:,:] = X[category_2,idx_2].reshape(w, h,1)

    return pairs, targets

batch_size를 통해 함수를 호출해야 하며, batch_size 수만큼 이미지의 쌍을 반환한다.

Comments