09LangChain实战课 - 深入理解Chain组件

89 阅读4分钟

我正在参加「豆包MarsCode AI练中学体验活动」详情请看:掘金小册上线 AI练中学功能 | 你的 AI 编程助教喊你免费领小册啦!

LangChain实战课 - 深入理解Chain组件

1. 课程引入

  • 回顾了LangChain的应用和功能,提出了“Chain”作为关键组件的重要性。

2. 什么是Chain

  • Chain用于链接LangChain的各个组件和功能,简化复杂应用程序的实现,并使之模块化。
  • Chain可以视为LangChain中的基本功能单元,内部封装一系列功能,外部可以组合串联。

3. LLMChain:最简单的链

  • LLMChain整合了PromptTemplate、语言模型(LLM)和Output Parser,封装了Model I/O流程。
  • 通过示例演示了不使用链和使用链的代码对比,展示了链的简洁性。

4. 链的调用方式

  • 直接调用:调用链对象时,会调用内部实现的__call__方法。
  • 使用字典输入:如果提示模板包含多个变量,可以使用字典一次性输入。
  • 通过run方法:等价于直接调用__call_函数。
  • 通过predict方法:类似于run,输入键被指定为关键字参数。
  • 通过apply方法:针对输入列表运行链,一次处理多个输入。
  • 通过generate方法:返回LLMResult对象,包含生成文本过程中的相关信息。

5. Sequential Chain:顺序链

  • 使用Sequential Chain将多个LLMChain串起来,形成一个顺序链。
  • 通过示例演示了如何使用Sequential Chain生成鲜花的知识性说明、评论和社交媒体文案。

6. 总结

  • LangChain提供的“链”帮助我们将多个组件连接起来,形成一系列组件的调用顺序。
  • 可以使用多种方法调用链,并根据需求选择不同的链。
  • LangChain中还自带大量其他类型的链,封装了各种功能。

7. 思考题

  1. 使用LLMChain重构第4课中鲜花描述的提示format和获取模型输出部分。
  2. 进一步将output_parser整合到LLMChain中,简化程序结构。
  3. 选择一个LangChain中的链(未使用过的类型),尝试使用它解决一个问题,并分享用例和代码。
思考题解答
1. 使用LLMChain重构第4课中鲜花描述的提示format和获取模型输出部分。

在第4课中,我们可能使用了以下代码来生成鲜花描述:

for flower, price in zip(flowers, prices):
    # 根据提示准备模型的输入
    input = prompt.format(flower_name=flower, price=price)
    # 获取模型的输出
    output = model(input) 
    # 解析模型的输出
    parsed_output = output_parser.parse(output)

使用LLMChain重构上述代码:

from langchain import PromptTemplate, OpenAI, LLMChain

# 定义模型和提示模板
model = OpenAI(temperature=0)
template = "{flower_name}售价为{price}元,请给出一个吸引人的描述。"

# 创建LLMChain
llm_chain = LLMChain(
    llm=model,
    prompt=PromptTemplate.from_template(template)
)

# 准备输入数据
flowers = ["玫瑰", "百合", "康乃馨"]
prices = ["50", "30", "20"]

# 使用LLMChain获取模型输出
for flower, price in zip(flowers, prices):
    result = llm_chain.run({"flower_name": flower, "price": price})
    print(result)
2. 进一步将output_parser整合到LLMChain中,简化程序结构。

我们可以将output_parser作为LLMChain的一个参数,这样LLMChain就会负责解析输出:

from langchain import PydanticOutputParser

# 假设我们有一个Pydantic模型定义
from pydantic import BaseModel
class FlowerDescription(BaseModel):
    description: str

# 创建输出解析器
output_parser = PydanticOutputParser(pydantic_object=FlowerDescription)

# 将output_parser整合到LLMChain中
llm_chain = LLMChain(
    llm=model,
    prompt=PromptTemplate.from_template(template),
    output_parser=output_parser
)

# 使用LLMChain获取模型输出并解析
for flower, price in zip(flowers, prices):
    result = llm_chain.run({"flower_name": flower, "price": price})
    print(result.description)  # 直接访问描述字段
3. 选择一个LangChain中的链(未使用过的类型),尝试使用它解决一个问题,并分享用例和代码。

让我们选择ConditionalChain,这个链可以根据条件执行不同的子链。例如,我们可以根据用户输入的长度来决定使用不同的模型:

from langchain import ConditionalChain

# 定义两个不同的LLMChain,根据不同的输入长度使用不同的模型
llm_chain_short = LLMChain(llm=OpenAI(temperature=0.5), prompt=PromptTemplate.from_template("Short input: {input}"))
llm_chain_long = LLMChain(llm=OpenAI(temperature=0.7), prompt=PromptTemplate.from_template("Long input: {input}"))

# 定义条件函数
def use_long_model(input_text):
    return len(input_text) > 50

# 创建ConditionalChain
conditional_chain = ConditionalChain(
    chains=[llm_chain_short, llm_chain_long],
    conditions=[lambda x: len(x) <= 50, use_long_model]
)

# 测试ConditionalChain
input_short = "This is a short input."
input_long = "This is a very long input that exceeds the length of fifty characters, requiring a different model to handle its complexity."

print(conditional_chain.run(input_short))
print(conditional_chain.run(input_long))

在这个例子中,ConditionalChain根据输入的长度选择使用llm_chain_shortllm_chain_long。这样的链可以用于处理不同复杂度的任务,提高程序的灵活性和效率。

8. 延伸阅读

  1. GitHub上各种各样的链。
  2. LLMChain的实现细节代码。

通过本节课,我们深入理解了LangChain中的Chain组件,学习了如何使用LLMChain和Sequential Chain来简化和模块化我们的应用程序。Chain不仅提高了代码的可读性和可维护性,还使得复杂功能的实现变得更加简单。通过思考题和延伸阅读,我们可以进一步探索LangChain中的其他链类型,并尝试将它们应用到实际问题中。