AISmarteasy – 시맨틱 커널 포크로 개발하기 2a – PromptTemplate – prompt engineering(1/3)

우리는 컴퓨터에게 할 일을 지시(instruction)하기 위해 프로그래밍 한다. 지금은 좀 더 좁게 ai에게 할 일을 지시하려고 한다, 좀 더 좁게는 llm에게. 이 영역으로만 보면 여전히 프로그래밍 하고 있는 것이다.

프로그래밍은 구조화된 방식으로, 정해진 약속대로 작성해야 한다.

새로운 프로그래밍 언어가 등장했다. 비구조화 된 자연어를 사용하는. llm은 자연어 모델이니, 자연어로 프로그래밍 하고 있고 이를 프롬프트(prompt)라 한다.

 

대상이 달라졌으니, 프로그래밍 방식도 달라져야 한다. 배울 것도 다르다.

프롬프트 프로그래밍을 공학 수준에서 다루기 위해 prompt engineering이 등장했다. 프로그래밍 방식에 프롬프트 라는 새로운 용어를 등장 시킨 것처럼, sw engineering의 한 부분에 포함하지 않고 prompt engineering을 등장 시켰다.

prompt engineering 내용 정리는  AI 연구, 교육 및 기술의 민주화를 목표로 하는, DAIR.AI의 Prompt Engineering Guide를 참조한다.


Hello, World!

프롬프트는 비구조화 된 자연어를 사용하기 때문에, 이미 갖춘 자연어 역량으로 hello world 해 볼 수 있다. llm이 잘 하는 것이 텍스트 생성이니, 텍스트 생성과 관련된 일을 하라고 지시하자. 궁금한 것을 묻는 것도 llm 입장에서는 응답을 생성하는 것이다. 프로그래밍 하려면 프로그래밍 언어를 지원하는 도구가 있어야 한다. llm 공급자는 프롬프트를 작성하고 실행할 수 있는 도구를 제공한다. open ai는 llm 공급자이고 playground를 제공한다. playground에서 궁금한 것을 작성해서 실행시키자. 도구 사용법 정도 배우면, 자연어를 사용하니 특별한 것을 더 배우지 않더라도 hello world는 끝난다.

 

LLM Settings

프로그램 실행 환경에 대한 설정이 필요하다. 프롬프트가 프로그램이고, llm이 실행 환경이다.

llm에서 설정해야 할 것들

  • temperature – 무작위성(randomness)
    • 0~2 사이의 값을 갖는다.
    • llm은 확률 기반 언어 모델로, 이미 나온 것을 기반으로 다음 토큰(단어)이 나올 확률을 가지고 다음 토큰을 예한다. 그 후에는 그 다음 단어를 예측한다. 이 과정을 반복 해 답변을 완성한다. 확률은 훈련된 데이터들로 결정된다. 확률이 높다는 것은 그 만큼 자주 사용되는 문장으로 더 일반적이라 할 수 있다. 더 일반적인 것을 정답이라고 한다면 정답에 더 가까운 것이 된다. 무작위성 값이 커진다는 것은 해당 토큰 배열이 더 가끔 씩 나온다는 것이고, 더 가끔 나오는 것을 더 창의적이라고 한다면 무작위성이 커질 수록 더 창의적이 된다.
      • 같은 질문이라도 사실적인 응답을 원하는 경우 temperature 값을 낮게, 창의적이고 상상력이 풍부한 응답을 원하는 경우 temperature 값을 높게 설정한다. 
  • top_p(nucleus sampling)
    • 0~1 사이의 값
    • 다음으로 나올 토큰을 찾을 때, 모든 토큰을 대상으로 하는 것이 아니라, 누적 확률이 이 값 이상이 되는 것들만 대상으로 한다.
    • 값이 낮을수록 더 높은 확률의 더 적은 토큰이 대상이 됨으로, 더 일반적이 된다. 이 값이 높을 수록 더 창의적 더 다양해 진다.
      • temperature와 같이 무작위성 영향을 미치는 것이니, temperature를 설정 했다면 이건 설정하지 않아도 된다.
  • max length – 응답을 생성할 때 사용할 최대 토큰 수
    • 보통 256, 512, 1024, 2048, 4096과 같이 2의 지수 승으로 작성한다. 응답을 길게 하게 하려면 이 값을 크게 한다.
  • stop sequence – 응답 생성을 중단할 때 쓸 문자열
    • 여러 개 등록할 수 있다.
  • frequency penalty – 반복 되는 토큰에 벌 점 부여.
    • 다음 단어를 선택할 때 이전 벌점으로 다음 토큰 선택에 반영 한다. 벌점이 높은 토큰, 많이 반복되어 나온 토큰은 다음 토큰으로 선택되기 어려워진다.
    • 0~2 사이의 값
  • presence penalty – 있으면 벌점 부여
    • frequency penalty는 토큰 사용이 반복될 수록 누적되고, presence penalty는 토큰 사용 자체에 주어지는 것이다.
    • 0~2 사이의 값

 

Elements of a Prompt

프롬프트는 llm을 위한 것으로 general 프로그래밍 보다는 도메인 specific 언어라고 보는 게 맞을 것 같다.

프롬프트는 구조가 없는 자연어로 작성하고, 모국어를 사용할 것이니 모국어 사용하는데 문제 없다면, 프롬프트 프로그래밍의 기본은 갖췄다고 할 수 있다. 프로그래밍을 더 잘하기 위한 과정 만 남았다.

프롬프트는 지시(instruction)를 작성하는 것이다. 지시 내용을 프로그래밍 하는 것이다. 지시 내용( input data)을 작성한다.

기본적인 프로그래밍은 끝났다.

 

단순하게 시킨 일만 하면 될까? 잘 해야 한다. 잘 한다는 것은 좀 더 신경 써서 해야 할 것들이 있다는 것. llm은 텍스트 생성이니 텍스트 생성할 때 신경 써야 할 것들이 있다는 것. 공손하게 답하라고 하던가 json 형식으로 답해 달라고 하는 것과 같은 응답 조건(output indicator)들이 있을 수 있다.

llm의 태생적 한계로, llm에 없는 데이터를 제공해야 할 수 있다. 이 부분을 context라 한다.

 

예) 감정 분석하라고 시키고 싶다. 지시 내용은 ‘감정 분석 해라’.

어떤 결과를 원하는가? 감정 분석 결과가 neutral, negative, positive가 되도록.

감정 분석할 내용은 Text 부분에, 결과를 Sentiment 부분에. 결과는 채워질 부분이니 프롬프트에는 비어 있다. 

감정 분석할 내용은 “I think the food was okay.”

위 내용을 반영해 작성한 프롬프트는

Classify the text into neutral, negative, or positive

Text: I think the food was okay.

Sentiment:

 

아무 프로그램이나 작성하는 게 아니다. llm이 잘 할 수 있는 일을 지시하는 프로그램을 짜야 한다. llm은 언어 모델로 질의 응답을 잘 한다. 텍스트 생성을 잘 한다. 텍스트 생성을 좀 더 구체화 하면, 요약, 분류, … 지금도 잘 하는 분야가 많다. 앞으로는 더 많아 질 것 같다.

General Tips

  • 간단하게 시작하자.
    • 지시 내용과 출력 조건을 작성하자.
    • 작성한 프롬프트를 llm에게 전달 해 보자. 결과를 보고 바꾸거나 보강할 내용을 작성하자. 만족스러운 결과가 나올 때 까지 여러 번 이 과정을 해 보자.
  • llm에 무엇을 지시할 지 목표 수준으로 정한다. llm이 잘 하는 것을 알면 도움이 된다.
    • 예)  분류, 요약, 번역
  • 목표 수준의 지시를 구체화한다. 목표 수준의 지시의 대상이 있다(input data). 불 필요한 고민을 없애기 위해 어떤 지시에 어떤 레이블을 사용할 것인지 미리 정해 두자. 이전 예에서는 지시 대상은 Text, 응답은 Sentiment를 사용.
  • 지시는 명확하게, 구체적으로 작성한다.
  • 원하는 형식으로 출력 되기를 원할 경우, 원하는 형식으로 llm이 출력하도록 하는 방법을 미리 알아보자. 대부분 방법이 공개되어 있을 것이다. 원하는 형식으로 출력하기 위해 어떻게 해야 하는 지가 공개되어 있지 않다면, llm 실행을 해 보면서 작성해 봐야 한다.
Extract the name of places in the following text.
Desired format:
Place: <comma_separated_list_of_company_names>
Input: “Although these developments are encouraging to researchers, much is still a mystery. “We often have a black box between the brain and the effect we see in the periphery,” says Henrique Veiga-Fernandes, a neuroimmunologist at the Champalimaud Centre for the Unknown in Lisbon. “If we want to use it in the therapeutic context, we actually need to understand the mechanism.“”

콤마로 분리된 리스트로 출력하게 할 때 “<comma_separated_list_of_company_names>” 이렇게 하면 된다고 알았다. 그렇게 해 본다.

Place와 Input 레이블을 사용한다. Input은 Place 보다 더 일반적으로 더 많은 곳에서 사용될 수 있다. 이런 레이블 사용은 패턴 화 할 수 있어 보인다.

 

  • 정확하게 구체적이고 직접적으로 지시하자. 특히 응답에 대해.
    • llm ai 서비스들이 점 점 더 좋아지다 보니, 프롬프트를 대충 작성해도 원하는 결과를 얻을 수 있다. 결과에 상관 없이 나올 수 있도록 기본기는 기본이 되게 하자.
  • 할 일을 지시해라.
    • 이것도 너무 당연하다. 하지 말아야 할 일 대신 해야 할 일로 지시하라는 것이다.

Examples of Prompts

아래 링크된 프롬프트 예들을 살펴보자. 예제 실행은 윈도우에서 Window 키 + C를 윈도우11 코파일럿으로 실행해 본다.

 

llm은 언어 모델로 자연어 처리(Natural Language Processing, NLP)가 기본이다.

NLP에서 하려고 했던 일 들 에는 다음과 같은 것들이 있다.

  • Named-entity recognition (NER) / classification
  • Entity linking
  • Temporal expression recognition / normalization
  • Co-reference resolution
  • Information extraction
  • Terminology extraction
  • Discourse parsing

llm은 언어 모델로, nlp에서 하려 했던 일들을 모두 잘 해 낸다. 이전 어떤 모델 보다 월등하게.

llm을 사용하면, 하고 싶은 nlp 처리를 지시로 잘 작성하면 된다.

 

llm이 잘 하는 대표적인 일이 요약, 번역, 질의 응답이다. 질의 응답은 훈련되지 않은 데이터에 대해서는 모른다는 태생적 한계가 있지만, 검색 증강 생성(RAG)과 같은 방법으로 보완되고 있다.

코딩도 잘 한다.

llm은 언어 모델이니 수학이나 추론을 잘 못하는 것은 당연하다. llm이 잘 못하는 부분이니 프롬프트 프로그램 할 때 주의해야겠지. 프롬프트 엔지니어링은 이런 부분을 보강하기 위한 노력이다. 프롬프트 프로그래밍 고급 – 기법이라고 생각할 수 있다.

Prompting Techniques – Level1

프롬프트 프로그래밍 기법을 배워보자.

 

[ Zero-Shot Prompting, Few-Shot Prompting ]

llm은 이전 토큰 들을 고려해 다음 토큰이 나올 확률로 문장을 만들어 가기 때문에, 이전 출현 토큰 들은 llm 입장에서는 다음을 진행하기 위한 중요한 사전 지식이 된다. 프롬프트에 작성되는 모든 토큰 들은 llm 입장에서 다음 토큰을 생성하기 위한 사전 지식인 것이다. 예시를 작성하는 이유도 llm에게 사전 지식을 제공하기 위해서 이다.

zero-shot은 예제를 포함하지 않는 거고, few-shot은 포함하는 것이다. llm 결과가 어떻게 나오든, 가능하면 few-shot으로 하자.

 

llm들은 챗으로 서비스 되는데, 대화 하는 과정이 결국은 사전 지식을 생성해 보도록 하는 것이다. 대화를 프롬프트 프로그래밍 하는 과정으로 생각하면서 대화 시작 부분을 사전 지식 생성 단계로 보자.

 

[ Chain-of-Thought Prompting ]

llm은 언어 모델로 추론에 약하다. 이를 보강하기 위한 방법으로 등장한 기법이 Chain-of-Thought이다.

Chain-of-Thought은 이름 그대로 생각의 사슬이다. 생각을 한 번에 하는 것이 아니다 작은 여러 단계로 나눠서 단계 별로 하는 것이다. 응답하려면 어떤 단계들을 어떤 순서로 거쳐야 되는 지 알면, 단계와 단계 별 예시를 포함해서 프롬프트를 작성하면 된다.

Chain-of-Thought은 문제를 던지고 답을 구해 달라는 지시에서 답을 구하는 과정이 복잡한 것일 때 풀이 과정을 포함하도록 한 것이다.

어떤 단계들로 어떤 순서로 해야 할 지 모른다면, “단계 별로 생각(Let’s think step by step)” 하라고 지시에 포함하면 된다.  어떤 단계가 필요한 지 모르니 예시를 포함할 수 없다. 이런 CoT를 zero-shot CoT라 한다.

 

지시가 길고 복잡하다면 지시도 여러 개로 분할 하고 싶을 것이다. 분할 된 지시마다 CoT로 응답하도록 하고.

분할 된 지시와 CoT응답 쌍 여럿을 예시로, 복잡하고 어려운 지시를 입력으로 해서 프롬프트를 작성해서 llm에 전달한다. 이런 과정은 수 작업하려면 꽤 귀찮은 일이니 자동화하고 싶을 거다. 이렇게 하는 것을 Automatic Chain-of-Thought (Auto-CoT)라 한다.

 

[ Self-Consistency ]

한 가지 방법만 있다면 선택 고민이 없겠지만, 방법이 여러가지라면, 선택하는 기준이 있어야 한다. 알고 있는 방법들이라면 규칙에 따라 어느 정도 일관되게  선택할 수 있다. 지시하는 사람이 모르는 방법들이라면, llm이 일관된 기준으로 방법을 선택할 수 있도록 기준으로 사용할 예시를 주도록 한다.

 

[ Generated Knowledge Prompting ]

llm이 사전 지식을 직접 생성해서 지시에 응답하도록 한다.

입력 텍스트와 그 관련 지식을 쌍으로  예시로 포함한다. 이렇게 하면 입력에 대해 지식을 생성하는 방법으로 응답한다. llm이 응답하기 위해 입력에 대한  지식도 응답으로 포함해서 생성한다. 답해야 하는 입력이라면 지식에 기반해 응답한다.

 

Prompting Techniques – Level2

[ Prompt Chaining ]

프롬프트 기반 개발 – 모듈화, 재 사용 가능한 프롬프트 – 프롬프트들을 엮어서(조립해서) 체인을 만든다. 체인은 여러 프롬프트들로 구성된다.

프롬프트 체인 기법으로 프롬프트를 작성할 수도 있겠지만, 이 영역부터는 어느 정도 전통적인 방법으로 작성된 프로그램의 도움을 받는 것이 좋아 보인다.  프롬프트 작성 만으로 프롬프트 체인 기법을 사용하려면, 프롬프트 사이에 응답이 연결되어야 함으로, ai 서비스는 챗 방식이어야 한다.

 

[ Tree of Thoughts (ToT)]

나무 가지가 여러 갈래로 뻗어 나가듯 방법들이 다양할 수 있을 때 사용할 수 있는 기법이다. 이런 경우는 전문가들의 주장이 여러 갈래로 나눠진 영역에서 출현한다.

나뭇가지를 따라 갈 때는 미리 앞의 가지들을 따라 가 볼 수도 있고, 뒤로 돌아와 다른 갈래로 갈 수도 있다. 이처럼 전문가 여럿이 논의 하면서 답을 찾을 때,  논의 중간 단계에서 서로의 의견을 살펴봐야 한다. 주장을 더 나갈 수도 있고, 주장을 돌이킬 수도 있어야 한다. 사용하는 도구도 다를 수  있다.

  • 답 해야 하는 문제를 작성한다.
    • 예) The question is…
    • 예) The task is:
  • 몇 단계를 거칠 것인지, 전문가는 단계마다 최소한 몇 명은 참여할 지 작성한다.
    • 예) Imagine three different experts are answering this question.
  • 논의가 어떠해야 하는 지, 전문가들이 논의 중 취해야 할 자세, 사용할 도구를 작성한다.
    • 공통적인 부분
      • 예) The process continues until a conclusive answer is found. Organize the entire response in a markdown table format.
      •  예) All experts will write down 1 step of their thinking, then share it with the group. Then all experts will go on to the next step, etc. If any expert realises they’re wrong at any point then they leave.
      • 예) Each expert will share their thought process in detail, taking into account the previous thoughts of others and admitting any errors. They will iteratively refine and expand upon each other’s ideas, giving credit where it’s due.
    • 특정 전문가의 부분
      • 예) Three experts with exceptional logical thinking skills are collaboratively answering a question using the tree of thoughts method.

[ Vocabulary]

프롬프트 작성할 때, 레이블을 일관성 있게 작성하자.

사용자가 제공하는 텍스트는 Input

rag로 제공되는 데이터 Context

llm이 생성하는 결과는 Output

CoT를 한 경우, 단계 별로 생각하자는 Let’s think step by step.

Generated Knowledge Prompting에서 생성 지식 부분에는 Knowledge

Directional Stimulus Prompting에서 Hint

 

About the Author
(주)뉴테크프라임 대표 김현남입니다. 저에 대해 좀 더 알기를 원하시는 분은 아래 링크를 참조하세요. http://www.umlcert.com/kimhn/

Leave a Reply

*