토큰화
토큰화
토큰화는 텍스트를 분석 단위로 끊는 과정이다. 이때 끊어진 하나하나를 토큰이라고 부른다. 토큰은 분석의 단위가 되며, 이는 언어마다 다르다.
영어는 보통 단어 단위로 자른다. 단어는 혼자 쓸 수 있는 단위를 말한다. 예를 들어, "The Apple Went Bad"는 빈칸 단위로 쉽게 자를 수 있다.
한국어는 형태소 단위로 자른다. 형태소는 의미가 있는 가장 작은 단위를 말한다. 형태소는 붙여 쓸 수도 있고 띄어 쓸 수도 있는데, 이는 맞춤법 규칙에 따라 달라진다.
일부 형태소는 의존 형태소라고 하는데, 이는 의미는 있지만 혼자 쓰지 못하는 형태소를 말한다. 예를 들어, '었'은 과거를 나타내지만 혼자 쓰지 못하고 '먹었다'와 같이 다른 단어와 붙여서만 쓸 수 있다.
중국어나 일본어 같은 경우, 단어 사이에 빈칸이 없어서 영어처럼 빈칸 단위로 자르는 것이 불가능하다. 이런 경우에는 별도의 단어 분리 과정이 필요하다.
형태소 분석
토큰화는 언어마다 다르기 때문에 각 언어에 맞는 토큰화 방법이 필요하다. 한국어의 경우 형태소로 자르게 되며, 이를 위해 형태소 분석기라는 별도의 소프트웨어나 라이브러리가 필요하다.
형태소 분석과 품사 태깅은 엄밀히 말하면 다르다. 형태소 분석은 단순히 자르는 것이고, 품사 태깅은 자른 후 품사를 붙이는 것이다. 하지만 보통 형태소 분석이라고 하면 품사 태깅까지 포함하는 경우가 많다.
형태소 분석은 규칙 기반과 통계 기반(머신러닝) 두 가지 방식으로 할 수 있다. 규칙 기반은 언어의 규칙을 모두 입력하는 방식이지만, 언어가 계속 변화하기 때문에 완벽하지 않다.
문법은 학교 문법, 규범 문법, 기술 문법으로 나눌 수 있다. 학교 문법은 학교에서 가르치는 것, 규범 문법은 마땅히 써야 한다고 생각하는 것, 기술 문법은 실제로 사용되는 방식을 말한다.
예를 들어, '했었었다'와 같은 표현은 학교 문법에는 맞지 않지만, 실제로 사용되고 있다. '사겼다'와 같은 새로운 발음도 생기고 있다.
이러한 변화 때문에 규칙 기반 방식만으로는 모든 경우를 처리할 수 없다. 따라서 최근의 형태소 분석기는 규칙과 머신러닝을 함께 사용하거나 머신러닝만을 사용하는 경향이 있다.
표제어 추출
영어의 경우 보통 띄어쓰기 단위로 토큰화하지 만, 때로는 단어의 원형을 찾아야 할 때가 있다. 그러나 이는 항상 필요한 것은 아니다. 예를 들어, 'may'와 'might', 'island'와 'islands'는 단순히 시제나 단복수의 차이가 아니라 의미가 다를 수 있기 때문이다.
'원형'이라는 용어는 실제로 언어학적 용어가 아니다. 언어학에서는 '표제어'라는 용어를 사용한다. 표제어는 사전에서 굵은 글씨로 쓰인 항목을 말한다.
자연어 처리에서는 '어간 추출'과 '표제어 추출'을 구분한다. 어간 추출은 간단한 규칙(휴리스틱)을 사용하여 단어의 어간을 찾는 방법이다. 예를 들어, 영어에서 '-ed'를 제거하는 방식이다. 그러나 이 방법은 정확하지 않을 수 있다.
표제어 추출은 단어가 사전에 어떻게 등재되어 있는지를 찾는 방법이다. 이 방법은 사전이 필요하며, 최근에는 기계학습을 활용하여 수행한다. 이는 모든 단어가 사전에 등재되어 있지 않기 때문이다.
영어로 표제어는 'lemma'라고 한다.
영어 자연어 처리 라이브러리
영어 자연어 처리를 위한 주요 라이브러리들이 있다. 가장 유명한 것은 NLTK(Natural Language Toolkit)인데, 이는 가장 오래되고 유명한 라이브러리이다. 하지만 오래되었다는 것은 전통적이거나 고전적인 방법론을 사용한다는 의미이기도 하다.
NLTK의 문제점은 한국어를 지원하지 않는다는 것이다. 따라서 NLTK를 중심으로 설명하는 책은 한국어 처리에 큰 도움이 되지 않는다.
CoreNLP는 자바로 만들어진 것을 파이썬에서 사용할 수 있게 한 라이브러리지만, 이 역시 한국어 처리에는 적합하지 않다.
Stanza와 spaCy는 딥러닝 기반의 라이브러리로, 둘 다 한국어를 지원한다. 하지만 이들도 한국어 처리에 있어서는 완벽하지 않다. 그 이유는 딥러닝을 위한 충분한 한국어 데이터가 없기 때문이다.
한국어 형태소 분석을 위해서는 단어를 손으로 분해한 데이터가 필요하다. 이런 데이터를 만들기 위해서는 많은 비용이 들지만, 현재 한국에서는 이에 대한 투자가 충분히 이루어지지 않고 있다. 따라서 데이터의 양이 적어 딥러닝을 통한 한국어 처리의 성능이 좋지 않다.
spacy
spacy를 설치하고 영어 모델을 다운로드하는 과정을 설명한다.
먼저, pip를 사용해 spacy를 설치한다:
pip install spacy
그 다음, 딥러닝 모델을 별도로 다운로드해야 한다. 모델 이름은 'en_core_web_sm'인데, 각 부분의 의미는 다음과 같다:
- 'en': English(영어)
- 'core_web': 핵심 웹 모델
- 'sm': Small(작은 크기)
딥러닝 모델은 크기가 클수록 성능이 좋지만, 다운 로드 시간이 오래 걸린다. 모델 크기는 보통 sm(small), md(medium), lg(large) 순으로 커진다. 여기서는 시간 관계상 'sm' 모델을 사용하지만, 실제 사용 시에는 더 큰 모델을 선택할 수 있다.
모델을 다운로드하는 명령어는 다음과 같다:
python -m spacy download en_core_web_sm
spacy를 사용하기 위해 먼저 라이브러리를 임포트한다. 그 다음, 앞서 다운로드한 "en_core_web_sm" 모델을 로드한다.
import spacy
nlp = spacy.load("en_core_web_sm")
분석할 영어 문장을 text 변수에 저장한다. 여기서는 "All work and no play makes Jack a dull boy."라는 문장을 사용했다. 이는 "일만 하고 놀지 않으면 바보가 된다"는 의미의 영어 속담이다.
text = "All work and no play makes Jack a dull boy."
nlp 함수에 text를 입력하여 분석을 수행하고, 그 결과를 doc 변수에 저장한다.
doc = nlp(text)
이 과정에서 주의할 점은 반드시 영어 모델(en으로 시작하는 모델)을 사용해야 한다는 것이다. 그래야 영어 문장을 올바르게 분석할 수 있다.
for token in doc:
print(token.text,
token.lemma_, # 표제어
token.pos_, # 단어의 품사
token.tag_, # 자세한 품사
token.is_stop) # 불용어 여부
doc에 분석 결과가 들어있고, 이를 하나씩 살펴볼 것이다. 파이썬 문법에 익숙하지 않은 사람들을 위해 설명하자면, 'for token in doc:'는 doc에 있는 토큰들을 하나씩 꺼내서 볼 것이라는 의미이다.
각 토큰에 대해 다음 정보를 출력한다:
- token.text: 토큰의 텍스트
- token.lemma_: 표제어
- token.pos_: 품사 (Part of Speech)의 대분류
- token.tag_: 품사의 소분류
- token.is_stop: 불용어 여부
'print' 함수를 사용해 이 정보들을 출력한다. 'for' 루프 안에 있는 코드는 들여쓰기를 해야 한다.
이 코드를 실행하면 문장의 각 토큰에 대해 위의 정보들이 출력될 것이다.
spacy.explain('PROPN')
각 용어의 의미는 위와 같이 확인할 수 있다
spacy 한국어 처리
모델 설치
python -m spacy download ko_core_news_sm
한국어 문장 처리
import spacy
nlp = spacy.load("ko_core_news_sm")
text = "오늘은 점심으로 뭘 먹을까?"
doc = nlp(text)
품사 태그는 영어로 복잡하게 나오는데, 한국어 처리 시에는 주로 다음과 같이 간단화한다:
명사:
- 동작성 명사: '하다'가 붙어 동사가 되는 단어
- 상태성 명사: '하다'가 붙어 형용사가 되는 단어
- 비서술성 명사: 일반 명사 (예: 꽃)
- 고유 명사
용언(동사와 형용사):
- 지시동사
- 일반 동사
- 성상형용사
한국어에서는 동사와 형용사의 구별이 어려운 경우가 많다. 예를 들면, "늙다"는 동사고, "젊다"는 형용사다. 텍스트 분석 시에는 이들을 구분할 필요 없이 용언으로 통합해서 사용한다.
분석에 포함시키는 품사는 주로 위의 명사와 용언 범주에 속하는 것들이다. 조사, 어미, 기호, 접두사, 접미사 등은 대체로 분석에서 제외한다.
이러한 방식으로 텍스트 분석에 필요한 주요 단어들을 선별할 수 있다.
문장 구조 분석
spacy.displacy.render(doc)
이 코드는 spaCy가 제공하는 문장 구조 시각화 기능을 사용한다. 문장을 어떻게 끊어 읽는지, 단어들 간의 관계가 어떤지를 보여준다.
예를 들어, "All work and no play makes Jack a dull boy" 문장에서:
- "makes"가 동사로 인식되고,
- "All work and no play"가 주어(nsubj)로 표시된다.
- "Jack"은 목적어로, "a dull boy"는 보어로 표시될 것이다.
이런 방식으로 문장의 구조를 시각적으로 보여준다. 학교에서 배웠던 '주어 찾기', '동사 찾기' 등의 작업을 컴퓨터가 자동으로 수행하는 것이다.
이 기능은 영어에서 매우 정확하게 작동하지만, 한국어에서는 아직 정확도가 떨어진다.