마스크 언어 모형으로 문장 중간의 빈 칸 예측
마스크 언어 모형 파이프라인을 초기화한다.
from transformers import pipeline
nlp = pipeline("fill-mask")
Some weights of RobertaForMaskedLM were not initialized from the model checkpoint at distilroberta-base and are newly initialized: ['lm_head.decoder.bias'] You should probably TRAIN this model on a down-stream task to be able to use it for predictions and inference.
마스크 토큰
nlp.tokenizer.mask_token
'<mask>'
파이프라인에 문장을 입력한다.
nlp(f"Pizza is my {nlp.tokenizer.mask_token} food")
[{'score': 0.4141102433204651, 'sequence': '<s>Pizza is my favorite food</s>', 'token': 2674, 'token_str': 'Ġfavorite'}, {'score': 0.31080567836761475, 'sequence': '<s>Pizza is my comfort food</s>', 'token': 5863, 'token_str': 'Ġcomfort'}, {'score': 0.138148233294487, 'sequence': '<s>Pizza is my favourite food</s>', 'token': 5548, 'token_str': 'Ġfavourite'}, {'score': 0.015286021865904331, 'sequence': '<s>Pizza is my dream food</s>', 'token': 3366, 'token_str': 'Ġdream'}, {'score': 0.013527910225093365, 'sequence': '<s>Pizza is my signature food</s>', 'token': 6543, 'token_str': 'Ġsignature'}]
빈 칸(마스크)가 2개 이상인 경우 직접 모형을 만들어야 한다.
from transformers import TFAutoModelForMaskedLM, AutoTokenizer
모형을 다운로드
tokenizer = AutoTokenizer.from_pretrained("distilroberta-base")
model = TFAutoModelForMaskedLM.from_pretrained("distilroberta-base")
토크나이저
vocab = tokenizer.get_vocab()
id2word = {i: word for word, i in vocab.items()}
문장
sequence = f"Pizza is my {tokenizer.mask_token} food."
토큰화
input_ids = tokenizer.encode(sequence, return_tensors="tf")
빈 칸의 위치 찾기
mask_token_indices = tf.where(input_ids[0] == tokenizer.mask_token_id)[0].numpy().tolist()
모형에 입력
result = model(input_ids)
로짓
logits = result[0]
빈 칸 위치
i = mask_token_indices[0]
i
5
빈 칸의 로짓
mask_token_logits = logits[0, i, :]
가장 로짓이 높은 토큰 10개
top = tf.math.top_k(mask_token_logits, k=10)
출력
for i in top.indices.numpy().tolist():
print(id2word[i])
Ġfavorite Ġcomfort Ġfavourite Ġsignature Ġdream Ġpreferred Ġpassion Ġstaple Ġbreakfast Ġeveryday
빈 칸이 2개인 경우
sequence = f"Pizza {tokenizer.mask_token} my {tokenizer.mask_token} food."
input_ids = tokenizer.encode(sequence, return_tensors="tf")
mask_token_indices = tf.where(input_ids[0] == tokenizer.mask_token_id)
mask_token_indices = tf.squeeze(mask_token_indices).numpy().tolist()
mask_token_indices
[3, 5]
각 빈 칸의 가장 로짓(=확률)이 높은 토큰들 출력
result = model(input_ids)
logits = result[0]
for i in mask_token_indices:
print(f'=== {i} ===')
mask_token_logits = logits[0, i, :]
top = tf.math.top_k(mask_token_logits, k=10)
for i in top.indices.numpy().tolist():
print(id2word[i])
=== 3 === Ġis Ġwas Ġas Ġbecomes Ġequals Ġfor Ġdelivers Ġmakes Ġand Ġwith === 5 === Ġfavorite Ġcomfort Ġfavourite Ġjunk Ġbreakfast Ġlunch Ġown Ġsnack Ġfried Ġpreferred