본문 바로가기

Data Analysis

기계학습 - Spark(3) - Word2Vec, CountVectorizer

Spark 교재중 Word2Vec, CountVectorizer 설명 페이지에는 샘플코드중 스칼라로 코딩된 부분을 이해한다. [링크]


Word2Vec


샘플 스칼라 코드에서  .map(Tuple1.apply) 이 부분을 이해해보자. 여기서 map함수는 키-값의 맵을 구성하는 것이 아니라 맵리듀스의 맵으로 이해하면 된다. Seq 문으로 구성한 목록의 모든 구성요소에 대해 Tuple1.apply를 적용한다. 여기서 apply 호출을 눈여겨 보자. 'apply'는 스칼라 개발언어에서 아주 중요한 개념중의 하나이다. Tuple1객체는 생성자를 통해 인스턴스로 생성될 때, 생성자 매개변수로 하나의 데이터를 받아 그 데이터 하나로 구성된 tuple이 된다. 아래는 간단한 예다.


scala> val t1 = new Tuple1("")

t1: (String,) = ("",)


scala> val t2 = Tuple1.apply("")

t2: (String,) = ("",)



new 연산자와 apply연산자는 같은 역할을 한다. 자바스크립트의 apply를 연상하면 도움이되겠다. 그러나 스칼라의 것과 자바스크립트의 것은 다르다. 앞서 .map(...)은 맵리듀스 호출이므로 목록의 모든 구성요소를 가지고 Tuple1.apply함수를 호출하고 그 결과를 묶어서 반환받는다.


다시 word2vec으로 돌아오자. 영어의 경우 어순이 문장의 뜻을 결정하는데 중요한 요소이다. 그렇기에 어떤 단어 앞뒤에 위치하는 것만을 학습해도 문장의 뜻을 파악하는데 큰 도움이 되거나 단어들을 분류해낼 수 있다. 어쨌든 분류를 하는 것이다. 분류의 대상은 단어 혹은 문장이 될 수도 있고 문자열로 표현되는 어떤 정보도 가능하다. 이론에 따르면 모든 대상마다 고유의 벡터공간을 갖고 시작해서 학습을 통해 점차 유사하게 분류되는 대상끼리 합쳐진 공간으로 취합되고 합쳐진 공간에서 각각의 벡터값을 갖게 된다. 이런 과정을 반복하다 보면 학습된 모델은 어떤 대상과 또 다른 대상이 유사한 것인지 아닌지 알게 된다. 즉, 유사한 것끼리 벡터값이 점점 같아지게 된다.


그럼 이런 벡터값을 결정하는 것은 무엇일까? 단어의 앞/뒤에 어떤 단어가 얼마나 자주 나타나는지에 대해 통계를 구하고 이를 바탕으로 벡터값들을 결정한다. 이건 영어권에서 생각해 낼 수 있는 방법이다. 영어의 어순은 중요하므로 어떤 단어의 앞/뒤에 어떤 것이 나타나는 빈도에 대한 통계는 중요한 지표이기 때문이다.


우리나라 말은 어순은 상관없고, 조사에 의해 문장 의미가 결정되므로, 조사에 따라 어순을 보정하는 작업을 먼저 하면 응용이 가능하다고 본다.


아직 실력이 부족해 Word2Vec에 대한 다양한 통계방법을 이해하지는 못하고 있다. 통계방법보다는 다양한 연관들을 어떻게 벡터 공간에 표시하는지가 궁금하다.