티스토리 뷰

 

사람 간의 대화에서 공유하는 지식이 비슷해야 말이 통하는 것처럼 챗봇도 사용자와 자연스런 대화를 하기 위해서는 사람만큼의 폭 넓은 배경지식을 가져야 한다. 대화는 사적인 영역뿐만 아니라 세상에 관한 내용도 포함하기 때문에 가족이나 친구, 사는 동네 등의 신상 명세에서부터 영화, 음악, 요리, 스포츠, 여행, 취미 등을 포함하여 역사, 지리, 경제, 사회 그리고 세세하게는 주요 건물의 이름, 관광지, 교통수단에 이르기까지 세상에 관한 지식을 폭 넓게 알고 있는 것이 필요하다. 많이 알면 알수록 대화가 자연스러워지겠으나 모든 것을 다 알게 만드는 데에는 시간이 많이 걸리므로 챗봇의 개발자가 잘 알고 있고 관심이 많은 분야를 선택해 지식을 구축해 가면 될 것이다.[1] 이 장에서는 K-POP이라는 분야를 예로 들어 지식을 구축하고 그 지식을 검색하는 방법을 알아 보기로 하겠다.

가장 먼저 할 일은 지식을 설계하는 일이다. CS에서 지식은 아래와 같은 3요소로 구성된다.

 

지식의 형식 : (주어 동사 목적어)

(박봄 멤버 투애니원)

(투애니원 히트곡 내가_제일__나가)

(테디 작곡 내가_제일__나가)

 

위와 같이 3가지 요소로 지식을 작성해 나가면 되는데, 이때 중요한 것은 두 번째 요소인 동사이다. 이 두 번째 요소에 사용할 단어는 같은 뜻일 때는 같은 단어로 사용해야 한다. 예를 들어 작곡가를 표시할 때 어떤 때는 작곡이라고 쓰고 어떤 때는 작곡하다”, 어떤 때는 “composer” 등으로 사용하면 안된다는 뜻이다. 동일한 내용을 가리킬 때 한 단어로 일관되게 작성해야 나중에 지식을 활용할 수 있기 때문이다.

지식을 작성한 후에는 다음과 같이 지식으로 만들어 지식베이스에 넣어 놓으면 된다. CS에서는 지식을 팩트(fact)라 부르며 그래서 명령어가 createfact 이다.

 

^createfact(박봄 멤버 투애니원)

^createfact (투애니원 히트곡 내가 제일 잘 나가”)

^createfact (테디 작곡 내가 제일 잘 나가”)

 

이제 새로운 지식이 만들어 졌다. 다시 말하지만 동사의 위치에 있는 멤버”, “히트곡”, “작곡은 챗봇의 작성자가 알 수 있는 임의의 단어이면 되지만 일관된 단어를 사용해야 나중에 지식으로 활용할 수 있다.

실수로 동일한 지식을 만들도록 명령하면 CS는 무시하므로 이 점은 걱정하지 않아도 된다. 그러나 서로 정반대의 의미를 갖는 내용을 지식으로 작성한다면 CS는 알 수 없으므로 이 점에 대해서는 개발자가 지식을 설계할 때 주의해야 한다.

어떤 분야이든 지식을 작성하려 하면 그 양이 무척 많다. 예를 들어 K-POP 가수들의 히트곡을 지식으로 작성하기로 하고 2000년 이후에 데뷔한 가수들과 대응하는 곡을 모두 작성한다면 많은 지식을 반복적으로 작성해야 한다. 이런 경우에는 Table 명령을 이용하면 좀 더 효율적으로 작성할 수 있다.

 

Table: 히트곡 (^singer ^hitsong)

^createfact(^singer 히트곡 ^hitsong)

Data:

투애니원 Falling_in_love

투애니원 I_love_you

투애니원 Ugly

투애니원 lonely

투애니원 내가_제일__나가

티아라 Cry_Cry

티아라 Day_by_Day

티아라 Number_nine

티아라 Bo_Peep_Bo_Peep

……

 

Table은 지식을 담고 있는 그릇이라고 생각하면 되는데, 소재별로 필요한 만큼 여러 개를 만들 수 있다. Table을 만들 때는 테이블의 이름, 인수, 수행할 액션, 데이터 지시자, 그리고 실제 데이터 이렇게 5개의 요소를 지정해 주면 된다. 위의 예에서 테이블 이름은 히트곡”, 인수는 ^singer ^hitsong 이렇게 두 개이며, 이 두 개의 인수를 받아 createfact 함수로 지식을 만드는 액션을 수행하고 있다. 인수의 이름은 작성자가 알아 볼 수 있도록 임의로 정하면 되며 개수에도 제한이 없다. 위의 예는 첫번째 인수를 주어(subject) 자리에 놓고 두번째 인수를 목적어(object) 자리에 놓으며 그 둘을 히트곡으로 연결한 지식을 만드는 예이다. 그리고 Data: 라는 키워드를 두고, 그 뒤에 실제 지식이 되는 두 개의 단어를 쌍으로 적어주면 된다.(Table의 인수가 두 개이므로 데이터도 두 개씩이다.)

이때 유의해야 할 점이 두 가지 있는데 첫번째는 띄어쓰기를 하는 고유명사는 _(언더바)로 연결해야 하나의 단어로 인식한다는 점이고, 두번째는 영문을 쓸 때 대소문자를 구별한다는 점이다. 예를 들어 위의 예에서 Ugly를 소문자 ugly로 적었다고 가정하면, 나중에 검색을 할 때 소문자 ugly로 찾아야 한다는 점이다. 이 점이 왜 중요한 지에 대해서는 다음 절에서 살펴보기로 하겠다. 지금은 대소문자를 구별한다는 점만 기억해 두기로 하자. 이상의 방법으로 새로 추가한 지식은 Topic 폴더 아래에 facts1.txt 라는 파일에 저장된다.

이제 지식베이스에서 지식을 찾는 방법에 대해 알아 보자. 질의문의 형식은 앞서 지식을 만들 때의 형식과 동일하다. 다만, 질의문을 작성하기 전에 무엇을 찾으려 하는지를 먼저 결정해야 한다. 예를 들면, 위의 예에서, 투애니원의 히트곡을 찾는 것인지(=주어와 동사를 지정하고 목적어를 찾음), Ugly를 히트곡으로 부른 가수를 찾는 것인지(=동사와 목적어를 지정하고 주어를 찾음), 아니면 투애니원과 관련된 것 모두를 찾는 것인지(=주어만 지정하고 동사와 목적어를 찾음) 등에 따라 질의문의 종류가 달라지기 때문이다.

 

^query(kind subject verb object)

 

첫번째 지시자 kind가 질의문의 종류를 표기하는 것이다. 만약 Ugly를 히트곡으로 가지고 있는 가수가 누구인지 알고 싶다면, 이는 동사와 목적어를 지정하고 주어를 알고 싶은 것이므로 kind 자리에 direct_vo를 적는다. 그리고 주어를 찾고 있으므로 주어 자리에 ?(물음표)를 적으면 된다.

 

^query(direct_vo ? 히트곡 ugly)

 

이 질의문은 동사 자리에 히트곡이 있고 목적어 자리에 “ugly”가 있는 주어를 모두 검색하라는 의미이다. 이 검색결과는 복수의 행과 복수의 열을 가진 값이 될 것이기 때문에 별도로 준비된 변수에 저장해야 한다.

 

@0 = ^query(direct_vo ? 히트곡 ugly)

 

@으로 시작하는 변수가 그것인데, 이 변수는 지식베이스에 있는 자료 구조와 동일하게 만들어진 변수로 한 행에 열을 3개씩 가지고 있다. , subject, verb, object 이다. 그리고 검색결과가 3개이면 차례로 0, 1, 2번에 저장이 된다. 따라서 @변수를 시각화 해 보면 아래와 같다.



위의 질의문이 실행되고 지식베이스에 ugly를 히트곡으로 가진 subject가 존재한다면 그 값은 @0subject에 저장하게 될 것이다. 그리고 이를 실제 대화문에 적용해 보면,

 

#! Ugly가 누구 히트곡이에요?

u: ( <<ugly*  히트곡*>> ) ^query(direct_vo ? 히트곡 ugly) @0subject 곡이에요.

 

사용자 입력문이 패턴과 일치하면, CS는 질의문을 수행하게 되는데 지식베이스에서 조건에 맞는 지식을 발견하면 @변수의 해당하는 위치에 값을 저장한다. 어디에 저장하라고 명시하지 않으면 자동으로 @0에 저장한다. 저장된 값을 사용할 때는 @의 자료구조에 맞춰 해당하는 위치의 변수명을 호출하면 된다. @변수는 @20까지 가능하다.

질의문은 조건으로도 사용될 수 있다. 결과값이 있으면 참이 되는 형식이다.

 

t: If(^query(direct_vo ? 원한다 장난감)) {@0subject 장난감을 갖고 싶어해요}

u: ( 강아지 ^query(direct_sv 강아지 먹는다 ?)) 우리집 강아지는 @0object 잘 먹어요.

 

지식은 작성자가 구축해 놓는 것이 보통이지만, 대화를 하면서 사용자가 입력한 내용을 지식으로 저장할 수도 있다.

 

#! 나는 크라이 크라이를 좋아해.

u: (* _*) ^createfact(%user 말했다 ‘_0) . 잘 기억해 두겠습니다.

          #! 내가 뭐라 말했니?

          a: (<<* 말했*>>) ^query(direct_sv %user 말했다 ?) . @0object 라고 말하셨습니다.

 

%user는 사용자의 로그인 네임을 알려주는 시스템 변수이고 말했다는 지식을 만들 때 작성자가 임의로 결정해 동사 자리에 넣은 단어이다. 위의 룰은 사용자가 말한 내용을 입력 형태 그대로 지식베이스로 구축해 준다.

동사 중에 member isa(is a 의 뜻)CS에 예약된 동사이니 이 두 단어를 쓸 때는 동일한 뜻으로 써야 한다. Member는 주어가 목적어에 포함된다는 뜻이고 isa는 주어와 목적어가 동등관계라는 뜻이다.

CS에서 제공하는 Table이라는 형태는 팩트(facts)를 기록하고 확인하는데 간편하면서도 효과적인 툴이다. 그럼에도 더 전문적인 자료 관리가 필요하다면 외부 데이타베이스와 연결하여 처리할 수 있다. CS는 공개 데이타베이스인 PostgreSQL과의 연결을 기본적으로 제공한다. 그 외에도 JSON을 통해 인터넷에서 실시간으로 검색을 할 수 있는 방법도 제공하고 있다.[2]


 




[1] 이 지식은 다른 사람이 작성한 것을 가져다 사용할 수도 있다. 소스 파일에는 영어로 작성된 방대한 지식이 포함되어 있다. RawData/WorldData 폴더 아래의 .tbl 파일을 참조.

[2] 이 두 가지 방법은 응용편에서 다루기로 하고 이곳에서는 언급만 하고 넘어가기로 하겠다소스와 함께 포함되어 있는 ChatScript PostgreSQL.pdf와 ChatScript JSON.pdf를 참고해도 된다.

댓글
댓글쓰기 폼