Data & Research
[LLM & RAG] Langchain 기초 - Chain
물박사의 저장공간
2025. 4. 3. 00:16
1. Chain의 연결방식
(1) LCEL (LangChain Expression Language) :
LangChain에서 제공하는 선언형(Declarative) 방식으로 체인을 구성하는 방법입니다. Python 코드로 직접 체인을 구성하지 않고, 직관적인 YAML 스타일의 표현식을 사용합니다. (비유하자면 R에서 파이프라인 연산자? 같이 쓰는 방식이라고 할까요?)
- 간결한 표현: 복잡한 체인도 짧은 코드로 정의 가능.
- 재사용성: 정의된 체인을 쉽게 재사용하거나 공유 가능.
- 시각적 구성 가능: LCEL 기반의 GUI 도구를 활용할 수도 있음.
from langchain_core.runnables import RunnableLambda
from langchain_openai import ChatOpenAI
from langchain_core.prompts import PromptTemplate
# LCEL 스타일 체인 구성
prompt = PromptTemplate.from_template("Tell me a short fact about {topic}")
llm = ChatOpenAI(model="gpt-4")
# LCEL 체인 연결
chain = prompt | llm
# 실행
print(chain.invoke({"topic": "space"}))
(2) Python 체인 방식 (Imperative 방식) :
Python 체인 방식은 명령형(Imperative) 방식으로 체인을 구성하는 방법입니다. 즉, 개발자가 SequentialChain, LLMChain 등의 클래스를 직접 사용해 체인을 연결하고 실행해야 합니다. 보다 세밀한 제어가 가능하지만, 코드 작성이 상대적으로 복잡할 수 있습니다.
from langchain.prompts import PromptTemplate
from langchain_openai import ChatOpenAI
template = "{language}로 사랑한다는 말을 번역해줘."
prompt_template = PromptTemplate.from_template(template)
prompt = prompt_template.format(language="영어")
llm = ChatOpenAI()
result = llm.invoke(prompt)
print(result)
2. Chain에 input을 주는 방식
아래와 같은 Chain이 있다고 해봅시다.
from langchain.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain.output_parsers import StrOutputParser
# 프롬프트 템플릿 정의
chat_prompt = ChatPromptTemplate.from_template("Tell me a fact about {topic}")
# LLM 설정
chat = ChatOpenAI(model="gpt-4")
# 출력 파싱
output_parser = StrOutputParser()
# 체인 구성
runnable = chat_prompt | chat | output_parser
1) invoke를 활용한 단일 입력 처리
invoke()는 하나의 입력값을 처리하는 동기(synchronous) 방식
결과가 완전히 생성된 후 반환
# 단일 입력 실행
result = runnable.invoke({"topic": "black holes"})
print(result)
2) batch를 이용한 다중 입력 처리
batch()는 여러 개의 입력을 병렬로 실행하여 속도 증가
invoke()를 여러 번 실행하는 것보다 효율적
# 여러 개의 입력을 리스트로 전달
batch_inputs = [
{"topic": "black holes"},
{"topic": "quantum mechanics"},
{"topic": "neural networks"}
]
# 배치 실행
batch_results = runnable.batch(batch_inputs)
# 결과 출력
for topic, result in zip(batch_inputs, batch_results):
print(f"Topic: {topic['topic']} → Result: {result}")
3) stream을 이용한 스트리밍 방식 처리
stream()은 모델이 생성하는 출력(토큰)을 실시간으로 반환
flush=True를 사용하면 터미널에서 즉시 출력
네트워크 응답을 기다리지 않고 빠르게 출력
# 스트리밍 방식으로 실행
for chunk in runnable.stream({"topic": "black holes"}):
print(chunk, end="", flush=True)
참고) 여러개의 Runnable을 병렬적으로 실행하기
from langchain.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain.schema.runnable import RunnableParallel
from langchain.output_parsers import StrOutputParser
# 첫 번째 프롬프트: 기본 정보 제공
prompt1 = ChatPromptTemplate.from_template("Tell me a fact about {topic}")
chat1 = ChatOpenAI(model="gpt-4")
output_parser = StrOutputParser()
chain1 = prompt1 | chat1 | output_parser
# 두 번째 프롬프트: 주어진 주제에 대한 장점 설명
prompt2 = ChatPromptTemplate.from_template("What are the benefits of {topic}?")
chat2 = ChatOpenAI(model="gpt-4")
chain2 = prompt2 | chat2 | output_parser
# RunnableParallel을 이용해 두 개의 체인을 병렬로 실행
parallel_chain = RunnableParallel(
fact_chain=chain1, # 첫 번째 체인
benefit_chain=chain2 # 두 번째 체인
)
# 실행 (병렬로 두 개의 체인이 동시에 실행됨)
result = parallel_chain.invoke({"topic": "quantum computing"})
# 결과 출력
print(result)
{
'fact_chain': 'Quantum computing leverages quantum mechanics to perform computations exponentially faster than classical computers in certain tasks.',
'benefit_chain': 'Quantum computing can solve complex problems in cryptography, drug discovery, and optimization much faster than classical computers.'
}