주제 : μ€‘고등학생을 μœ„ν•œ ν•™κ³Ό κ΅μˆ˜λ‹˜ 인터뷰 챗봇

의의 : λŒ€ν•™ 진학 μ „, μœ μš©ν•œ 정보λ₯Ό 얻을 수 있음!

 

결과 미리보기 :

μ•„μš°.. 우리 λͺ¨λΈ λ‹΅λ³€ 잘 λ½‘μ•„λƒ…λ‹ˆλ‹€^0^

 

ν•™μŠ΅μ— ν•„μš”ν•œ 데이터셋 :

컀리어넷 학과인터뷰
λ°μ΄ν„°μ…‹μ˜ ν˜•νƒœ

ν•™κ³Όμ˜ κ°œμˆ˜λŠ” 총 320κ°œκ°€ 있으며, 평균 μ§ˆμ˜μ‘λ‹΅ κ°œμˆ˜λŠ” 11쌍, μ΅œλŒ€ 19쌍 κΉŒμ§€ μ΄μ–΄μ§‘λ‹ˆλ‹€.

 

λ°μ΄ν„°μ…‹μ˜ λŒ€ν‘œ 질문:

1.κ΅μˆ˜λ‹˜κ»˜μ„œ 전곡 μ„ νƒν•œ 동기이 λ¬΄μ—‡μΈκ°€μš”
2.μ–΄λ–€ 뢄야에 관심 κ°–λŠ” μ‚¬λžŒμ΄ 이 ν•™κ³Όλ‘œ 였면 μ’‹μ„κΉŒμš”
3.이 ν•™κ³Όμ—μ„œ κ°€μž₯ μ€‘μš”ν•œ κ³΅λΆ€λŠ” μ–΄λ–€ λ‚΄μš©μΈκ°€μš”
4.이 ν•™κ³Όμ—μ„œ 곡뢀 μž˜ν• λ €λ©΄ μ€‘κ³ λ“±ν•™μƒλ•Œ μ–΄λ–€ ꡐ과λͺ©μ„ κ³΅λΆ€ν•˜λ©΄ μ’‹μ€κ°€μš”
5.이 ν•™κ³Όμ˜ μž₯점은 λ­”κ°€μš”
6.이 ν•™κ³Όμ˜ 학생듀이 κ²ͺλŠ” 어렀움은 λ­”κ°€μš”
7.ν•™κ³Ό 쑸업생이 κ°€μž₯ 많이 μ§„μΆœν•˜λŠ” μ§μ—…λΆ„μ•ΌλŠ” μ–΄λŠ κ³³μΈκ°€μš”
8.ν•™κ³Όμ˜ μ•žμœΌλ‘œμ˜ 전망은 μ–΄λ–€κ°€μš”
9.μ§€κΈˆμ€ μ—†μ§€λ§Œ μ•žμœΌλ‘œ μƒˆλ‘œ μƒκΈ°κ²Œ 될 직업은 μ–΄λ–€κ²Œ μžˆλ‚˜μš”
10.이 ν•™κ³Όλ₯Ό μ „κ³΅ν•˜λ €λŠ” 학생이 진학 전에 곡뢀해야 될것이 μžˆλ‹€λ©΄ μ–΄λ–€κ±΄κ°€μš”
11.이 ν•™κ³Όλ₯Ό μ§€λ§ν•˜λŠ” μ€‘κ³ λ“±ν•™μƒν•œν…Œ λ§ˆμ§€λ§‰ ν•œλ§μ”€ ν•΄μ£Όμ„Έμš”

 

좔가적인 아이디어

λ”±λ”±ν•œ 닡변이 μ•„λ‹Œ, λ¬Έμž₯을 ν•˜λ‚˜μ”© λ§ν•˜λ“―μ΄ λ‚΄λ±‰μœΌλ©΄μ„œ 감정을 뢙이면 쒋을 λ“― ν–ˆλ‹€!

이걸 μ–΄μΌ€ν•˜λŠλƒ

 

Emotion Recognition in Conversation

MELD 데이터셋

λŒ€ν™” λ‚΄μ—μ„œ λ°œν™”μžμ˜ 감정을 μΈμ‹ν•˜λŠ” Taskκ°€ 있음. 이λ₯Ό ERC라고 함.

κ°μ •μ˜ μ’…λ₯˜

μœ„μ˜ MELD λ°μ΄ν„°μ…‹μ—λŠ” 총 7개의 감정이 μžˆλŠ”λ°, μœ„μ˜ 사진과 κ°™μŒ!!

κ·Έλž˜μ„œ μ΄λŸ¬ν•œ ERC λͺ¨λΈμ„ ν•©μΉ˜λ©΄ 감정 ν‘œν˜„ κ°€λŠ₯.

 

Overview

전체적인 μ‹œμŠ€ν…œμ˜ 흐름

1. 인터뷰 ν•™μŠ΅

인터뷰λ₯Ό μœ„ν•΄ 데이터셋을 ν•™μŠ΅ν•  λͺ¨λΈμ΄ ν•„μš”ν•¨. 본인은 KoGPTλ₯Ό 선택함!

λͺ¨λΈ ν•™μŠ΅μ„ μœ„ν•œ 데이터셋 μ „μ²˜λ¦¬

데이터 μ „μ²˜λ¦¬ν•΄μ„œ 질문-λ‹΅λ³€ 총 2개의 column으둜 κ΅¬μ„±ν–ˆκ³ , 총 4,259개의 쌍이 λ‚˜μ˜΄.

but,

γ…‹γ…‹γ„Ήγ…ƒγ…ƒ

GPU의 ν•œκ³„λ‘œ Fine-Tuning λΆˆκ°€ν–ˆμŒ.

λ”°λΌμ„œ In-context Learning을 μ‚¬μš©ν•΄μ„œ μΆ”λ‘ ν•˜κΈ°λ‘œ 함. 

 

2. λ²ˆμ—­

감정인식을 ν•˜κΈ° μœ„ν•΄μ„œ λ²ˆμ—­μž‘μ—…μ΄ ν•„μš”ν–ˆμŠ΅λ‹ˆλ‹€.

κ΅¬κΈ€μ˜ Translate 라이브러리 μ‚¬μš©ν•΄μ„œ ν•œκ΅­μ–΄ > μ˜μ–΄λ‘œ λ³€ν™˜ν•΄μ£Όμ—ˆμŠ΅λ‹ˆλ‹€.

 

3. 감정 인식

Emotion English DistilRoBERTa-base

챗봇이 λ§ν•˜λŠ” λ¬Έμž₯의 감정을 μΈμ‹ν•΄μ•Όν•˜λ‹ˆ 이와 λ§žλŠ” λͺ¨λΈμ„ ν•™μŠ΅ν•˜κ±°λ‚˜ μ°Ύμ•„μ•Όμ£ .

μ €λŠ” ν—ˆκΉ…νŽ˜μ΄μŠ€μ—μ„œ Emotion English DistilRoBERTa-baseλΌλŠ” λͺ¨λΈμ„ κ°€μ§€κ³ μ™”μŠ΅λ‹ˆλ‹€!

μ–˜λŠ” μ™Όμͺ½μ— λ³΄μ΄λŠ” λ°μ΄ν„°μ…‹μœΌλ‘œ ν•™μŠ΅ν–ˆλ‹€κ³  ν•©λ‹ˆλ‹€.

 

이 λͺ¨λΈμ„ μ‚¬μš©ν•œ κ²°κ³Όλ₯Ό 보면

쨘

μ•„μ£Ό 잘 인식 ν•˜λ„€μš”. 예제λ₯Ό λ„£μœΌλ©΄ λ²ˆμ—­μ„ 톡해 각각의 감정에 λ”°λ₯Έ ν™•λ₯ κ°’을 λ³΄μ—¬μ€λ‹ˆλ‹€. sadnessκ°€ κ°€μž₯ ν¬λ„€μš”.

이제 이 감정을 이λͺ¨μ§€λ‘œ ν‘œν˜„ν• κ±°μ—μš”

emoji 라이브러리

νŒŒμ΄μ¬μ—λŠ” 이런 λΌμ΄λΈŒλŸ¬λ¦¬κ°€ μžˆμ–΄μš”! 이λͺ¨μ§€λ₯Ό 좜λ ₯ν•΄μ€λ‹ˆλ‹€.

μš°λ¦¬κ°€ ν‘œν˜„ν•΄μ•Όν•˜λŠ” κ°μ •μ˜ 이λͺ¨μ§€ 이름을 μ°Ύμ•„λ³΄λ‹ˆ μ•„λž˜μ™€ 같이 λ‚˜μ™”μŠ΅λ‹ˆλ‹€!

호호호

이제 μ•„κΉŒ κ΅¬ν•œ 졜고 ν™•λ₯ κ°’κ³Ό 이 이λͺ¨μ§€λ₯Ό 1λŒ€1 맀칭 ν•΄μ£Όλ©΄ μ΄λ ‡κ²Œ λ©λ‹ˆλ‹€!

감정 ON

자 이러고 μ²˜μŒμ— ν•œκΈ€λ‘œ 좜λ ₯된 κ²°κ³Όκ°’κ³Ό 이λͺ¨μ§€λ₯Ό 합쳐주면 전체적인 overview μ„€λͺ… 끝!

이제 κ²°κ³Όλ₯Ό λ‹€μ‹œλ³ΌκΉŒμš”?

λŒ€λ‹΅μ΄ μ• λ§€ν•œ 경우λ₯Ό λ½‘μ•„μ™”λ„€μš”

μ§„μ§œ 잘 뽑을 땐 λ†€λžκ²Œ μž˜λ½‘μ•„μš”!! 

 

이러고 λΈ”λ‘œκ·Έ μ—…λ‘œλ“œλ₯Ό μœ„ν•΄ κ°„κ²°ν•œ μ½”λ“œλ₯Ό μ œμž‘ν•˜μ—¬ μ²¨λΆ€ν•˜μ˜€μŠ΅λ‹ˆλ‹€.

 

이상 GPTλ₯Ό μ‚¬μš©ν•˜μ—¬ λ§Œλ“  ν•œκ΅­μ–΄ ν•™κ³Ό 인터뷰 챗봇 μ œμž‘κΈ°μ˜€μŠ΅λ‹ˆλ‹€.

κ°μ‚¬ν•©λ‹ˆλ‹€.

 

κ΅¬ν˜„μ„ μœ„ν•œ κ°„λ‹¨ν•œ μ½”λ“œ!

더보기

100쀄도 μ•ˆλ˜μ₯¬?

import time
import torch
from transformers import AutoTokenizer, AutoModelForCausalLM
from transformers import pipeline
import emoji
import googletrans


classifier = pipeline("text-classification", model="j-hartmann/emotion-english-distilroberta-base", return_all_scores=True)

change = {'anger' : ":face_with_symbols_on_mouth:",
          'disgust' : ":nauseated_face:",
          'fear' : ":fearful_face:",
          'joy' : ":grinning_face:",
          'neutral' : ":neutral_face:",
          'sadness' : ":loudly_crying_face:",
          'surprise' : ":astonished_face:"
          }

translator = googletrans.Translator()

tokenizer = AutoTokenizer.from_pretrained(
    'kakaobrain/kogpt', revision='KoGPT6B-ryan1.5b-float16',  # or float32 version: revision=KoGPT6B-ryan1.5b
    bos_token='[BOS]', eos_token='[EOS]', unk_token='[UNK]', pad_token='[PAD]', mask_token='[MASK]'
)
model = AutoModelForCausalLM.from_pretrained(
    'kakaobrain/kogpt', revision='KoGPT6B-ryan1.5b-float16',  # or float32 version: revision=KoGPT6B-ryan1.5b
    pad_token_id=tokenizer.eos_token_id,
    torch_dtype='auto', low_cpu_mem_usage=True
).to(device='cuda', non_blocking=True)
_ = model.eval()


def gpt_interview(prompt, max_length: int = 256, ends_interview: bool = False):
    with torch.no_grad():
        model.eval
        tokens = tokenizer.encode(prompt, return_tensors='pt').to(device='cuda', non_blocking=True)
        gen_tokens = model.generate(tokens, do_sample=True, temperature=0.8, max_length=max_length)
        generated = tokenizer.batch_decode(gen_tokens)[0]
    generated_answer = generated[len(prompt):]
    end_idx = generated_answer.index('Q')
    return generated[len(prompt):len(prompt) + end_idx - 1]
    
try:
    major = input("<챗봇이 μ—°κ²°λ˜μ—ˆμŠ΅λ‹ˆλ‹€.> \n μ–΄λŠ ν•™κ³Ό κ΅μˆ˜λ‹˜κ³Ό 인터뷰 ν• κΉŒμš”? \n User: ")

time.sleep(2)
first = input(f'{major} κ΅μˆ˜λ‹˜κ³Ό 인터뷰λ₯Ό μ§„ν–‰ν•˜κ² μŠ΅λ‹ˆλ‹€. μ§ˆλ¬Έμ„ ν•΄μ£Όμ„Έμš”. \n User:')

prompt = f"""{major} κ΅μˆ˜λ‹˜κ³Ό 인터뷰λ₯Ό μ§„ν–‰ν•˜κ² μŠ΅λ‹ˆλ‹€.
Q:{first}
A:"""

user = ''
while user!="μ’…λ£Œ":
    chatbot = gpt_interview(prompt, max_length=300)

    for sentence in chatbot.split('.'):
        try:
            ko_en = translator.translate(sentence, dest='en', src='ko')

            emotion = classifier(ko_en.text)
            top_emotion = ""
            top_score = 0
            for num in range(len(emotion[0])):
                if top_score < emotion[0][num]['score']:
                    top_emotion = emotion[0][num]['label']
                    top_score = emotion[0][num]['score']
            print(f"\n{major}κ΅μˆ˜λ‹˜: {sentence}{emoji.emojize(change[top_emotion])}")
            time.sleep(1)
        except:
            continue

    user = input('\nUser: ')
    prompt = f"""{major} κ΅μˆ˜λ‹˜κ³Ό 인터뷰λ₯Ό μ§„ν–‰ν•˜κ² μŠ΅λ‹ˆλ‹€.
    Q:{user}
    A:"""
728x90
λ°˜μ‘ν˜•
Liky