feat: cot example

This commit is contained in:
zxmfke
2025-03-20 16:05:40 +08:00
parent f518fc59b7
commit 2f59b3e798
7 changed files with 312 additions and 0 deletions
+102
View File
@@ -0,0 +1,102 @@
# Chain of Thought (CoT) 模式实现
本文档介绍了 OpenManus 中的 Chain of Thought (CoT) 模式实现及使用方法。
## 什么是 Chain of Thought
Chain of Thought(思维链)是一种提示大语言模型展示其推理过程的方法,通过显示模型如何一步步思考问题,从而得出更准确的结论。与 ReActReasoning and Acting)模式不同,CoT 专注于思考过程的展示,而不涉及工具的使用和执行。
## CoT 与 ReAct 的区别
|特性|CoT(思维链)|ReAct(推理行动)|
|---|---|---|
|主要目的|展示详细的思考过程|执行操作并与环境交互|
|使用工具|不使用工具|使用各种工具执行操作|
|步骤数|通常只需一步完成|多步骤循环(思考-行动-观察)|
|适用场景|复杂推理、数学问题、逻辑题|任务执行、信息检索、编程等|
|输出重点|思考过程和最终答案|工具调用结果和执行状态|
## 实现概述
CoT 模式的实现包括以下文件:
1. `app/agent/cot.py` - CoT 代理实现
2. `app/prompt/cot.py` - CoT 特定的提示模板
CoT Agent 继承自 BaseAgent,实现了一个简单的思考步骤,不包含工具调用。
## 使用方法
### 方法一:使用选择器脚本
使用项目根目录的 `select_agent.py` 脚本,可以选择不同的代理模式:
```bash
python select_agent.py
```
然后选择 "2" 使用 CoT 模式。
### 方法二:直接运行示例
项目包含两个示例脚本:
1. 基本 CoT 示例:
```bash
python examples/cot_agent_example.py
```
2. 多步骤 CoT 对话示例:
```bash
python examples/multi_step_cot_example.py
```
### 方法三:在代码中使用
在你的代码中使用 CoT 代理:
```python
from app.agent import CoTAgent
async def main():
agent = CoTAgent()
result = await agent.run("你的问题或提示")
print(result)
```
## 定制 CoT
要定制 CoT 的行为,可以修改以下部分:
1. 修改系统提示:编辑 `app/prompt/cot.py` 中的 `SYSTEM_PROMPT`
2. 调整输出格式:通过修改系统提示中的指示来改变输出格式
3. 增加特定领域知识:根据需要在系统提示中添加特定领域的专业知识或指导
## 高级用法
### 多步骤推理
对于需要多步推理的复杂问题,可以设置更多的步骤:
```python
agent = CoTAgent(max_steps=3)
```
然后使用 `step()` 方法进行逐步推理,在每步之间可以添加新的用户输入。
### 与其他模式结合
可以考虑将 CoT 与其他模式结合使用,例如:
- 先使用 CoT 分析问题和制定计划
- 然后使用 ReAct 执行具体操作
## 故障排除
如果遇到以下问题:
1. **回答过于简短**:调整系统提示,强调需要详细的思考过程
2. **没有遵循格式**:检查系统提示中的格式指导,确保清晰明确
3. **性能问题**:CoT 适合较复杂的推理任务,对于简单问题可能显得冗长
+2
View File
@@ -1,5 +1,6 @@
from app.agent.base import BaseAgent
from app.agent.browser import BrowserAgent
from app.agent.cot import CoTAgent
from app.agent.planning import PlanningAgent
from app.agent.react import ReActAgent
from app.agent.swe import SWEAgent
@@ -9,6 +10,7 @@ from app.agent.toolcall import ToolCallAgent
__all__ = [
"BaseAgent",
"BrowserAgent",
"CoTAgent",
"PlanningAgent",
"ReActAgent",
"SWEAgent",
+45
View File
@@ -0,0 +1,45 @@
from typing import List, Optional
from pydantic import Field
from app.agent.base import BaseAgent
from app.logger import logger
from app.llm import LLM
from app.prompt.cot import NEXT_STEP_PROMPT, SYSTEM_PROMPT
from app.schema import AgentState, Message
class CoTAgent(BaseAgent):
"""Chain of Thought Agent - Focuses on demonstrating the thinking process of large language models without executing tools"""
name: str = "cot"
description: str = "An agent that uses Chain of Thought reasoning"
system_prompt: str = SYSTEM_PROMPT
next_step_prompt: Optional[str] = NEXT_STEP_PROMPT
llm: LLM = Field(default_factory=LLM)
max_steps: int = 1 # CoT typically only needs one step to complete reasoning
async def step(self) -> str:
"""Execute one step of chain of thought reasoning"""
logger.info(f"🧠 {self.name} is thinking...")
# If next_step_prompt exists and this isn't the first message, add it to user messages
if self.next_step_prompt and len(self.messages) > 1:
self.memory.add_message(Message.user_message(self.next_step_prompt))
# Use system prompt and user messages
response = await self.llm.ask(
messages=self.messages,
system_msgs=[Message.system_message(self.system_prompt)] if self.system_prompt else None
)
# Record assistant's response
self.memory.add_message(Message.assistant_message(response))
# Set state to finished after completion
self.state = AgentState.FINISHED
return response
+15
View File
@@ -0,0 +1,15 @@
SYSTEM_PROMPT = """You are an assistant focused on Chain of Thought reasoning. For each question, please follow these steps:
1. Break down the problem: Divide complex problems into smaller, more manageable parts
2. Think step by step: Think through each part in detail, showing your reasoning process
3. Synthesize conclusions: Integrate the thinking from each part into a complete solution
4. Provide an answer: Give a final concise answer
Your response should follow this format:
Thinking: [Detailed thought process, including problem decomposition, reasoning for each step, and analysis]
Answer: [Final answer based on the thought process, clear and concise]
Remember, the thinking process is more important than the final answer, as it demonstrates how you reached your conclusion.
"""
NEXT_STEP_PROMPT = "Please continue your thinking based on the conversation above. If you've reached a conclusion, provide your final answer."
+33
View File
@@ -0,0 +1,33 @@
#!/usr/bin/env python3
"""
CoT Agent Example - Demonstrates how to use Chain of Thought mode for reasoning
"""
import asyncio
import sys
from pathlib import Path
# Add project root directory to path
sys.path.append(str(Path(__file__).resolve().parent.parent))
from app.agent import CoTAgent
from app.logger import logger
async def main():
# Create CoT agent
agent = CoTAgent()
# Provide a problem that requires thinking
question = "Zhang, Li, and Wang have a total of 85 apples. Zhang has twice as many apples as Li, and Wang has 5 more apples than Li. How many apples does each person have?"
logger.info(f"Question: {question}")
# Run the agent and get results
result = await agent.run(question)
logger.info(f"Execution complete!")
if __name__ == "__main__":
asyncio.run(main())
+55
View File
@@ -0,0 +1,55 @@
#!/usr/bin/env python3
"""
Multi-step CoT Agent Example - Demonstrates how to use Chain of Thought mode in multi-turn conversations
"""
import asyncio
import sys
from pathlib import Path
# Add project root directory to path
sys.path.append(str(Path(__file__).resolve().parent.parent))
from app.agent import CoTAgent
from app.logger import logger
from app.schema import Message
async def main():
# Create CoT agent
agent = CoTAgent(max_steps=3) # Set maximum steps to 3
# Initial question
initial_question = "As artificial intelligence technology develops, what ethical challenges might we face?"
logger.info(f"Initial question: {initial_question}")
# Add initial question to agent's memory
agent.memory.add_message(Message.user_message(initial_question))
# Step 1: Get initial thoughts
logger.info("Step 1: Initial thoughts")
response1 = await agent.step()
print(f"\nResponse:\n{response1}\n")
# Step 2: Ask follow-up question
follow_up_question = "Among the ethical challenges you mentioned, which one do you think is most urgent to address? Why?"
logger.info(f"Follow-up question: {follow_up_question}")
agent.memory.add_message(Message.user_message(follow_up_question))
response2 = await agent.step()
print(f"\nResponse:\n{response2}\n")
# Step 3: Ask final follow-up
final_question = "Can you suggest some specific solutions for addressing this most urgent ethical challenge?"
logger.info(f"Final question: {final_question}")
agent.memory.add_message(Message.user_message(final_question))
response3 = await agent.step()
print(f"\nResponse:\n{response3}\n")
logger.info("Multi-step CoT conversation complete!")
if __name__ == "__main__":
asyncio.run(main())
+60
View File
@@ -0,0 +1,60 @@
#!/usr/bin/env python3
"""
Agent Selector - Allows users to choose different agent modes
"""
import asyncio
import sys
from app.agent import CoTAgent
from app.agent.manus import Manus
from app.logger import logger
async def run_cot_agent():
"""Run Chain of Thought agent"""
agent = CoTAgent()
prompt = input("Enter your question: ")
if not prompt.strip():
logger.warning("Empty question provided")
return
logger.warning("Processing your question...")
result = await agent.run(prompt)
logger.info("Question processing completed")
async def run_react_agent():
"""Run ReAct agent (Manus)"""
agent = Manus()
prompt = input("Enter your request: ")
if not prompt.strip():
logger.warning("Empty request provided")
return
logger.warning("Processing your request...")
await agent.run(prompt)
logger.info("Request processing completed")
async def main():
print("\nSelect the agent mode to use:")
print("1. ReAct mode - Can use tools to execute tasks")
print("2. Chain of Thought (CoT) mode - Shows detailed thinking process")
choice = input("\nEnter option (1 or 2): ").strip()
if choice == "1":
await run_react_agent()
elif choice == "2":
await run_cot_agent()
else:
print("Invalid choice, please enter 1 or 2")
if __name__ == "__main__":
try:
asyncio.run(main())
except KeyboardInterrupt:
logger.warning("Operation interrupted")
sys.exit(0)