Skip to main content

PA-RAG (Preference Alignment RAG)

PA-RAG는 생성 모델이 검색된 문서를 충실하게 활용하도록 선호도 정렬(Preference Alignment)을 적용하는 RAG 아키텍처입니다. DPO(Direct Preference Optimization) 방식으로 검색 결과에 근거한 답변을 선호하고 환각된 답변을 비선호하도록 학습하여, 검색-생성 간의 정렬을 최적화합니다.

핵심 아이디어

기존 RAG에서 생성 모델은 검색된 문서를 컨텍스트로 받지만, 문서의 내용을 무시하고 자신의 사전 지식에 의존하여 환각된 답변을 생성하는 경우가 빈번합니다. PA-RAG는 이 문제를 선호도 학습으로 해결합니다.
  • 생성 모델이 검색 문서를 무시하고 자체 지식으로 답변 (환각 위험)
  • 검색 결과에 정답이 있어도 모델이 다른 답변을 생성
  • 검색기와 생성기 간의 정렬(alignment)이 부재
  • 검색 품질이 좋아도 생성 품질이 따라가지 못하는 병목

동작 방식

PA-RAG는 학습 파이프라인과 추론 파이프라인으로 구분됩니다.

학습 파이프라인

1

후보 답변 생성

동일한 질문과 검색 문서에 대해 여러 후보 답변을 생성합니다. temperature를 높여 다양한 답변을 샘플링합니다.
2

충실도 평가

각 후보 답변이 검색 문서에 얼마나 충실한지 평가합니다. 문서에 근거한 답변은 높은 점수, 환각된 답변은 낮은 점수를 받습니다.
3

선호 쌍 구축

충실도가 높은 답변을 chosen(선호), 낮은 답변을 rejected(비선호)로 쌍을 구성합니다.
4

DPO 학습

구축된 선호 쌍으로 생성 모델을 DPO 학습하여, 검색 문서에 충실한 답변을 생성하도록 정렬합니다.

추론 파이프라인

학습이 완료된 모델은 별도의 검증 단계 없이도 검색 결과에 충실한 답변을 생성합니다. 아래 LangGraph 구현은 추론 파이프라인을 시뮬레이션하며, 다수 후보 생성 + 충실도 평가 + 최선 선택 방식으로 PA-RAG의 핵심 아이디어를 근사합니다.

LangGraph 구현

PA-RAG의 원래 방식은 DPO로 모델 자체를 학습시키는 것입니다. 아래 구현은 학습 없이 추론 시점에서 동일한 효과를 근사하는 방식으로, 다수 후보 중 가장 충실한 답변을 선택합니다.

상태 정의

from typing import TypedDict, List
from langchain_core.documents import Document

class PARAGState(TypedDict):
    question: str
    documents: List[Document]
    candidate_answers: List[str]
    faithfulness_scores: List[float]
    answer: str

노드 함수

from langchain.chat_models import init_chat_model
from langchain_openai import OpenAIEmbeddings
from langchain_chroma import Chroma
from langchain_core.prompts import ChatPromptTemplate
from langchain_core.output_parsers import StrOutputParser

llm = init_chat_model("gpt-4o-mini", temperature=0)

embeddings = OpenAIEmbeddings()
vectorstore = Chroma(collection_name="documents", embedding_function=embeddings)
retriever = vectorstore.as_retriever(search_kwargs={"k": 4})

def retrieve(state: PARAGState) -> PARAGState:
    """벡터 데이터베이스에서 문서를 검색합니다."""
    question = state["question"]
    documents = retriever.invoke(question)
    return {"documents": documents}

그래프 구성

from langgraph.graph import StateGraph, START, END

workflow = StateGraph(PARAGState)

# 노드 추가
workflow.add_node("retrieve", retrieve)
workflow.add_node("generate_candidates", generate_candidates)
workflow.add_node("score_faithfulness", score_faithfulness)
workflow.add_node("select_best", select_best)

# 엣지 연결
workflow.add_edge(START, "retrieve")
workflow.add_edge("retrieve", "generate_candidates")
workflow.add_edge("generate_candidates", "score_faithfulness")
workflow.add_edge("score_faithfulness", "select_best")
workflow.add_edge("select_best", END)

# 컴파일
app = workflow.compile()

실행

result = app.invoke({"question": "RAG에서 환각을 줄이는 방법은?"})
print(result["answer"])

Self-RAG vs PA-RAG

항목Self-RAGPA-RAG
핵심 메커니즘Reflection Token으로 자기 평가선호도 정렬(DPO)로 생성 모델 학습
환각 방지 시점추론 시 (생성 후 검증)학습 시 (선호도 정렬) + 추론 시
추가 학습Reflection Token 생성 학습DPO 선호도 학습
추론 비용높음 (매 단계 평가)낮음 (학습된 모델이 직접 생성)
검증 방식근거 + 유용성 평가 (IsSup, IsUse)충실도 기반 선호 쌍
재시도기준 미달 시 재생성 루프불필요 (정렬된 모델이 충실한 답변 생성)
외부 소스사용하지 않음사용하지 않음

학습 데이터 구축

PA-RAG의 핵심은 고품질 선호 쌍(preference pair)을 구축하는 것입니다.
  1. 질문-문서 쌍 준비: 학습 데이터셋의 각 질문에 대해 검색을 수행하여 관련 문서를 확보합니다
  2. 다수 후보 생성: 동일한 질문 + 문서 조합으로 temperature를 높여 여러 답변을 샘플링합니다
  3. 충실도 자동 평가: 각 답변의 충실도를 자동 평가합니다
    • NLI(Natural Language Inference) 모델로 문서-답변 간 함의 관계 측정
    • 또는 별도의 LLM Judge로 충실도 점수 부여
  4. 쌍 구성: 동일 질문에 대해 충실도가 높은 답변(chosen)과 낮은 답변(rejected)을 쌍으로 묶습니다
  5. DPO 학습: 구축된 선호 쌍으로 DPO 학습을 수행합니다
PA-RAG의 추론 시 비용은 Self-RAG보다 낮습니다. Self-RAG는 매 생성마다 반사 토큰 평가와 재시도 루프가 필요하지만, PA-RAG는 학습 단계에서 정렬이 완료되므로 추론 시에는 단일 생성으로 충분합니다.
선호 쌍의 품질이 학습 결과에 직접적으로 영향을 미칩니다. 충실도 평가가 부정확하면 오히려 환각을 강화할 수 있으므로, 평가 모델의 신뢰성을 사전에 검증해야 합니다.

참고 논문

논문학회링크
PA-RAG: RAG Alignment via Multi-Perspective Preference Optimization (Chen et al., 2025)-arXiv 2501.01080