文思AI产品笔记
首页
最新文章
AI编程
AI架构
关于我
  • AI生态圈
  • AI大模型
  • 多维表格
  • AI创业笔记
  • AI落地案例
  • 个人产品推介
  • 问题集
  • 简体中文
  • English
首页
最新文章
AI编程
AI架构
关于我
  • AI生态圈
  • AI大模型
  • 多维表格
  • AI创业笔记
  • AI落地案例
  • 个人产品推介
  • 问题集
  • 简体中文
  • English
  • AI架构

    • AI架构

Prompt工程与上下文管理

掌握与AI对话的艺术:从基础到高级的Prompt设计与优化

📋 概述

Prompt工程是AI应用开发的核心技能之一。好的Prompt能够显著提升AI的输出质量、准确性和可控性。本文将系统介绍Prompt设计的原理、模式和最佳实践。

🎯 Prompt工程基础

什么是Prompt?

Prompt是给AI模型的指令或输入,它决定了模型的输出质量和方向。

基本结构:

[系统指令] + [上下文信息] + [用户问题] + [输出格式要求]

Prompt的核心要素

1. 清晰性(Clarity)

# ❌ 模糊的Prompt
"写点关于AI的东西"

# ✅ 清晰的Prompt
"写一篇800字的文章,介绍AI在医疗领域的3个主要应用场景,包括具体案例。"

2. 具体性(Specificity)

# ❌ 过于宽泛
"帮我分析这个数据"

# ✅ 具体明确
"""
请分析以下销售数据:
- 计算月度增长率
- 识别销售高峰期
- 提出3条优化建议
- 以表格和要点形式呈现

数据:[...]
"""

3. 上下文(Context)

# ❌ 缺少上下文
"这个方案可行吗?"

# ✅ 提供充分上下文
"""
背景:我们是一家电商平台,日活10万用户
目标:降低20%的客服成本
方案:使用AI客服替代50%的人工客服
限制:预算50万,3个月上线

请评估这个方案的可行性,从技术、成本、时间三个维度分析。
"""

4. 格式化(Format)

# ❌ 未指定格式
"列出AI的应用"

# ✅ 指定格式
"""
请列出AI的5个主要应用领域,按以下格式:

1. 【领域名称】
   - 应用场景:
   - 典型案例:
   - 市场规模:
   - 技术难度:⭐⭐⭐⭐⭐
"""

🔧 Prompt设计模式

1. 角色扮演模式(Role Playing)

原理:让AI扮演特定角色,提供专业视角

模板:

def role_playing_prompt(role: str, task: str) -> str:
    return f"""
你是一位{role}。

{task}

请以{role}的专业角度回答。
"""

# 示例
prompt = role_playing_prompt(
    role="资深Python工程师,有10年开发经验",
    task="请review以下代码,指出潜在问题和优化建议"
)

实战案例:

# 技术面试官
"""
你是一位资深的技术面试官,擅长评估候选人的技术能力和解决问题的思维方式。

面试题目:设计一个分布式缓存系统

候选人回答:[...]

请评估候选人的回答,从以下维度打分(1-10分):
1. 系统设计完整性
2. 技术选型合理性
3. 可扩展性考虑
4. 容错机制设计
5. 性能优化思路

并给出具体的反馈建议。
"""

# 医疗顾问
"""
你是一位有20年临床经验的全科医生,擅长诊断常见疾病。

患者症状:
- 持续发热38.5°C(3天)
- 咳嗽有痰
- 喉咙疼痛
- 轻微头痛

请提供:
1. 可能的诊断(3个)
2. 建议的检查项目
3. 初步用药建议
4. 注意事项

注意:这只是初步建议,请强调患者需要就医确诊。
"""

2. 思维链模式(Chain of Thought, CoT)

原理:引导AI展示推理过程,提高复杂任务的准确性

基础CoT:

def basic_cot_prompt(problem: str) -> str:
    return f"""
问题:{problem}

请一步一步思考:
1. 首先,分析问题的关键信息
2. 然后,列出解决步骤
3. 接着,执行每个步骤
4. 最后,给出最终答案

让我们开始:
"""

# 示例:数学问题
prompt = """
问题:一个商店原价100元的商品,先打8折,再减20元,最后又打9折,请问最终价格是多少?

请一步一步计算:
"""

# AI回答:
# 1. 原价:100元
# 2. 第一步打8折:100 × 0.8 = 80元
# 3. 第二步减20元:80 - 20 = 60元
# 4. 第三步打9折:60 × 0.9 = 54元
# 最终价格:54元

Zero-shot CoT:

# 只需在问题后加上 "让我们一步一步思考"
prompt = """
问题:如果5个人5天吃5个苹果,那么10个人10天吃多少个苹果?

让我们一步一步思考:
"""

Few-shot CoT:

prompt = """
示例1:
问题:一个班级有30个学生,其中60%是女生,女生中有一半喜欢数学。请问有多少女生喜欢数学?
思考过程:
1. 总学生数:30人
2. 女生人数:30 × 60% = 18人
3. 喜欢数学的女生:18 × 50% = 9人
答案:9人

示例2:
问题:一本书300页,小明第一天读了全书的1/3,第二天读了剩余的1/2,请问还剩多少页?
思考过程:
1. 总页数:300页
2. 第一天读:300 × 1/3 = 100页,剩余200页
3. 第二天读:200 × 1/2 = 100页,剩余100页
答案:100页

现在请解决:
问题:{your_problem}
思考过程:
"""

3. 自我一致性模式(Self-Consistency)

原理:多次生成答案,选择最一致的结果

实现:

import asyncio
from collections import Counter

class SelfConsistencyPrompt:
    def __init__(self, llm, n_samples=5):
        self.llm = llm
        self.n_samples = n_samples
    
    async def generate_with_consistency(self, prompt: str) -> str:
        # 生成多个答案
        tasks = [self.llm.generate(prompt) for _ in range(self.n_samples)]
        responses = await asyncio.gather(*tasks)
        
        # 提取最终答案(假设答案在最后一行)
        answers = [r.strip().split('\n')[-1] for r in responses]
        
        # 选择最常见的答案
        answer_counts = Counter(answers)
        most_common_answer = answer_counts.most_common(1)[0][0]
        
        # 找到包含该答案的完整响应
        for response in responses:
            if most_common_answer in response:
                return response
        
        return responses[0]

# 使用
prompt = """
问题:公司有100名员工,平均年龄30岁。新招了10名平均年龄25岁的员工,请问现在公司员工的平均年龄是多少?

让我们一步一步计算,并在最后一行给出答案(格式:答案:XX岁):
"""

consistency = SelfConsistencyPrompt(llm, n_samples=5)
result = await consistency.generate_with_consistency(prompt)

4. 程序辅助模式(Program-Aided)

原理:让AI生成代码来解决问题,提高准确性

示例:

prompt = """
问题:计算复利投资回报。初始投资10000元,年利率8%,投资10年,每年复利一次。

请用Python代码计算:
```python
# 你的代码

然后执行代码并给出答案。 """

AI生成:

principal = 10000  # 本金
rate = 0.08  # 年利率
years = 10  # 年数

final_amount = principal * (1 + rate) ** years
profit = final_amount - principal

print(f"最终金额:{final_amount:.2f}元")
print(f"投资收益:{profit:.2f}元")

输出:

最终金额:21589.25元

投资收益:11589.25元

"""


### 5. 思维树模式(Tree of Thoughts)

**原理**:探索多个推理路径,选择最优解

**实现**:
```python
class TreeOfThoughts:
    def __init__(self, llm):
        self.llm = llm
    
    def solve(self, problem: str, num_branches=3, depth=3):
        """
        使用思维树方法解决问题
        """
        # 第一层:生成多个初始思路
        initial_prompt = f"""
问题:{problem}

请提供{num_branches}种不同的解决思路,每种思路一段话:
"""
        initial_thoughts = self.llm.generate(initial_prompt)
        
        # 评估每个思路
        evaluation_prompt = f"""
以下是{num_branches}种解决思路:

{initial_thoughts}

请评估每种思路的可行性(1-10分)和理由:
"""
        evaluations = self.llm.generate(evaluation_prompt)
        
        # 选择最优思路并深入
        best_thought_prompt = f"""
基于以下评估:

{evaluations}

请选择最有希望的思路,并详细展开具体步骤:
"""
        detailed_solution = self.llm.generate(best_thought_prompt)
        
        return detailed_solution

# 使用
tot = TreeOfThoughts(llm)
problem = "设计一个日活百万的社交应用,如何降低服务器成本?"
solution = tot.solve(problem)

📝 上下文管理

1. 上下文窗口

概念:模型一次能处理的最大token数量

常见模型的上下文窗口:

  • GPT-3.5-Turbo:4K / 16K
  • GPT-4:8K / 32K
  • Claude 3:200K
  • Gemini 1.5 Pro:1M

Token估算:

import tiktoken

def count_tokens(text: str, model: str = "gpt-3.5-turbo") -> int:
    encoding = tiktoken.encoding_for_model(model)
    return len(encoding.encode(text))

# 示例
text = "这是一段测试文本"
tokens = count_tokens(text)
print(f"Token数量:{tokens}")

2. 上下文压缩

策略1:摘要压缩

class ContextCompressor:
    def __init__(self, llm, max_tokens=2000):
        self.llm = llm
        self.max_tokens = max_tokens
    
    def compress(self, long_text: str) -> str:
        current_tokens = count_tokens(long_text)
        
        if current_tokens <= self.max_tokens:
            return long_text
        
        # 压缩比例
        compression_ratio = self.max_tokens / current_tokens
        
        prompt = f"""
请将以下文本压缩到原来的{compression_ratio:.0%}长度,保留核心信息:

{long_text}

压缩后的文本:
"""
        
        compressed = self.llm.generate(prompt)
        return compressed

# 使用
compressor = ContextCompressor(llm, max_tokens=1000)
compressed_text = compressor.compress(long_document)

策略2:关键信息提取

def extract_key_information(text: str, llm) -> dict:
    prompt = f"""
从以下文本中提取关键信息:

{text}

请提取:
1. 主题(1句话)
2. 关键人物/实体
3. 重要事件/观点(3-5条)
4. 数据和数字
5. 结论

以JSON格式输出。
"""
    
    response = llm.generate(prompt)
    return json.loads(response)

策略3:分块处理

class ChunkedProcessor:
    def __init__(self, llm, chunk_size=2000, overlap=200):
        self.llm = llm
        self.chunk_size = chunk_size
        self.overlap = overlap
    
    def process_long_text(self, text: str, question: str) -> str:
        # 分块
        chunks = self.split_text(text)
        
        # 处理每个块
        chunk_results = []
        for i, chunk in enumerate(chunks):
            prompt = f"""
这是长文档的第{i+1}部分:

{chunk}

问题:{question}

如果这部分包含答案,请回答;如果没有,回答"无相关信息"。
"""
            result = self.llm.generate(prompt)
            if "无相关信息" not in result:
                chunk_results.append(result)
        
        # 整合结果
        if not chunk_results:
            return "文档中未找到相关信息"
        
        synthesis_prompt = f"""
以下是从文档不同部分提取的信息:

{chr(10).join(chunk_results)}

请整合这些信息,给出完整的答案:
"""
        
        final_answer = self.llm.generate(synthesis_prompt)
        return final_answer
    
    def split_text(self, text: str) -> list:
        words = text.split()
        chunks = []
        
        for i in range(0, len(words), self.chunk_size - self.overlap):
            chunk = ' '.join(words[i:i + self.chunk_size])
            chunks.append(chunk)
        
        return chunks

3. 对话历史管理

策略1:滑动窗口

class ConversationManager:
    def __init__(self, max_history=10):
        self.max_history = max_history
        self.messages = []
    
    def add_message(self, role: str, content: str):
        self.messages.append({
            "role": role,
            "content": content
        })
        
        # 保持最近的消息
        if len(self.messages) > self.max_history:
            # 保留系统消息
            system_messages = [m for m in self.messages if m["role"] == "system"]
            recent_messages = self.messages[-self.max_history:]
            self.messages = system_messages + recent_messages
    
    def get_context(self) -> list:
        return self.messages

策略2:重要性筛选

class ImportanceBasedHistory:
    def __init__(self, llm, max_messages=10):
        self.llm = llm
        self.max_messages = max_messages
        self.all_messages = []
    
    def add_message(self, role: str, content: str):
        self.all_messages.append({
            "role": role,
            "content": content,
            "importance": None
        })
    
    def get_context(self) -> list:
        if len(self.all_messages) <= self.max_messages:
            return self.all_messages
        
        # 评估每条消息的重要性
        for msg in self.all_messages:
            if msg["importance"] is None:
                msg["importance"] = self.evaluate_importance(msg)
        
        # 排序并选择最重要的
        sorted_messages = sorted(
            self.all_messages,
            key=lambda x: x["importance"],
            reverse=True
        )
        
        important_messages = sorted_messages[:self.max_messages]
        
        # 按时间顺序返回
        important_messages.sort(key=lambda x: self.all_messages.index(x))
        
        return important_messages
    
    def evaluate_importance(self, message: dict) -> float:
        prompt = f"""
评估以下对话消息的重要性(0-1分):

消息:{message["content"]}

评分标准:
- 包含关键信息:+0.3
- 包含决策或结论:+0.3
- 被后续对话引用:+0.2
- 纯寒暄或过渡:-0.3

只输出一个0-1之间的数字:
"""
        
        score = float(self.llm.generate(prompt).strip())
        return score

策略3:摘要保存

class SummarizedHistory:
    def __init__(self, llm):
        self.llm = llm
        self.current_messages = []
        self.summary = ""
    
    def add_message(self, role: str, content: str):
        self.current_messages.append({
            "role": role,
            "content": content
        })
        
        # 每10条消息,生成摘要
        if len(self.current_messages) >= 10:
            self.create_summary()
    
    def create_summary(self):
        conversation_text = "\n".join([
            f"{m['role']}: {m['content']}"
            for m in self.current_messages
        ])
        
        prompt = f"""
请总结以下对话的关键信息:

{conversation_text}

摘要应包括:
1. 主要讨论的话题
2. 达成的结论或决定
3. 待解决的问题

摘要:
"""
        
        new_summary = self.llm.generate(prompt)
        
        # 合并到总摘要
        if self.summary:
            self.summary = f"{self.summary}\n\n{new_summary}"
        else:
            self.summary = new_summary
        
        # 清空当前消息,只保留最近3条
        self.current_messages = self.current_messages[-3:]
    
    def get_context(self) -> str:
        context_parts = []
        
        if self.summary:
            context_parts.append(f"之前的对话摘要:\n{self.summary}")
        
        if self.current_messages:
            recent_conversation = "\n".join([
                f"{m['role']}: {m['content']}"
                for m in self.current_messages
            ])
            context_parts.append(f"\n当前对话:\n{recent_conversation}")
        
        return "\n\n".join(context_parts)

🎨 高级Prompt技巧

1. 情感引导

技巧:适当的情感表达能影响AI的输出风格

# 正式场景
"""
作为一位专业的商业顾问,请严谨地分析以下商业计划...
"""

# 创意场景
"""
发挥你的想象力!让我们一起头脑风暴,想出10个超酷的产品创意...
"""

# 教学场景
"""
想象你正在教一个10岁的孩子,请用简单有趣的方式解释量子力学...
"""

2. 反面提示

技巧:明确告诉AI不要做什么

prompt = """
请写一篇关于AI伦理的文章。

要求:
✅ 提供具体案例
✅ 多角度分析
✅ 结构清晰

避免:
❌ 不要使用行业黑话
❌ 不要过度技术化
❌ 不要超过1000字
❌ 不要抄袭已有文章
"""

3. 迭代优化

技巧:通过多轮对话逐步优化

# 第一轮:初稿
prompt_1 = "写一段产品介绍"

# 第二轮:改进
prompt_2 = "这段介绍太平淡了,请加入更多卖点和情感元素"

# 第三轮:精修
prompt_3 = "很好!请再精简到100字以内,更加punchy"

4. 约束与激励

技巧:设置约束和奖励机制

prompt = """
任务:为新产品设计营销方案

约束条件:
- 预算不超过10万
- 时间周期1个月
- 目标用户是18-25岁年轻人

激励目标:
如果方案能达到以下目标,视为优秀:
- 预期触达用户 > 10万
- 转化率 > 5%
- ROI > 3

请设计3个方案,并说明哪个方案最可能达到激励目标。
"""

5. 元Prompt

技巧:让AI帮你生成更好的Prompt

meta_prompt = """
我需要一个Prompt来完成以下任务:
{task_description}

目标用户:{target_audience}
期望输出:{expected_output}
约束条件:{constraints}

请帮我设计一个高质量的Prompt,要求:
1. 清晰具体
2. 包含必要的上下文
3. 指定输出格式
4. 包含few-shot示例(如果需要)

生成的Prompt:
"""

# 示例
task = "让AI帮我分析用户反馈"
audience = "产品经理"
output = "结构化的分析报告,包含情感分析、问题分类、优先级排序"
constraints = "需要处理中英文混合的反馈,识别具体的产品功能点"

generated_prompt = llm.generate(meta_prompt.format(
    task_description=task,
    target_audience=audience,
    expected_output=output,
    constraints=constraints
))

📊 Prompt评估与优化

1. 评估指标

class PromptEvaluator:
    def __init__(self, llm):
        self.llm = llm
    
    def evaluate(self, prompt: str, test_cases: list) -> dict:
        results = {
            'accuracy': 0,
            'relevance': 0,
            'completeness': 0,
            'clarity': 0,
            'consistency': 0
        }
        
        for test_case in test_cases:
            response = self.llm.generate(prompt.format(**test_case['input']))
            
            # 准确性
            accuracy = self.check_accuracy(response, test_case['expected'])
            results['accuracy'] += accuracy
            
            # 相关性
            relevance = self.check_relevance(response, test_case['input'])
            results['relevance'] += relevance
            
            # 完整性
            completeness = self.check_completeness(response, test_case['requirements'])
            results['completeness'] += completeness
            
            # 清晰度
            clarity = self.check_clarity(response)
            results['clarity'] += clarity
        
        # 一致性(多次运行)
        consistency = self.check_consistency(prompt, test_cases[0])
        results['consistency'] = consistency
        
        # 平均分
        n = len(test_cases)
        for key in results:
            if key != 'consistency':
                results[key] /= n
        
        return results
    
    def check_accuracy(self, response: str, expected: str) -> float:
        # 使用AI评估
        eval_prompt = f"""
回答:{response}
期望:{expected}

评估回答的准确性(0-1分):
"""
        score = float(self.llm.generate(eval_prompt))
        return score

2. A/B测试

class PromptABTest:
    def __init__(self, llm):
        self.llm = llm
    
    def compare(self, prompt_a: str, prompt_b: str, test_cases: list) -> dict:
        results_a = []
        results_b = []
        
        for test_case in test_cases:
            # 测试Prompt A
            response_a = self.llm.generate(prompt_a.format(**test_case))
            score_a = self.evaluate_response(response_a, test_case)
            results_a.append(score_a)
            
            # 测试Prompt B
            response_b = self.llm.generate(prompt_b.format(**test_case))
            score_b = self.evaluate_response(response_b, test_case)
            results_b.append(score_b)
        
        # 统计分析
        import numpy as np
        
        mean_a = np.mean(results_a)
        mean_b = np.mean(results_b)
        
        # 简单的显著性检验
        from scipy import stats
        t_stat, p_value = stats.ttest_ind(results_a, results_b)
        
        return {
            'prompt_a_avg': mean_a,
            'prompt_b_avg': mean_b,
            'winner': 'A' if mean_a > mean_b else 'B',
            'improvement': abs(mean_a - mean_b) / min(mean_a, mean_b),
            'p_value': p_value,
            'significant': p_value < 0.05
        }

3. 自动优化

class PromptOptimizer:
    def __init__(self, llm):
        self.llm = llm
    
    def optimize(self, initial_prompt: str, test_cases: list, iterations=5):
        current_prompt = initial_prompt
        best_score = 0
        best_prompt = initial_prompt
        
        for i in range(iterations):
            # 评估当前prompt
            score = self.evaluate(current_prompt, test_cases)
            
            if score > best_score:
                best_score = score
                best_prompt = current_prompt
            
            # 生成改进建议
            improvement_prompt = f"""
当前Prompt:
{current_prompt}

测试结果:
- 平均得分:{score}
- 主要问题:[从测试用例分析]

请提供3个改进建议,并生成优化后的Prompt。

优化后的Prompt:
"""
            
            improved_prompt = self.llm.generate(improvement_prompt)
            current_prompt = improved_prompt
        
        return {
            'best_prompt': best_prompt,
            'best_score': best_score,
            'iterations': iterations
        }

💡 最佳实践总结

Do's ✅

  1. 明确具体:清楚说明期望的输出
  2. 提供上下文:给足够的背景信息
  3. 使用示例:Few-shot提升效果
  4. 指定格式:明确输出格式要求
  5. 迭代优化:测试和改进Prompt
  6. 角色设定:让AI扮演合适的角色
  7. 分步推理:复杂任务使用CoT
  8. 设置约束:明确不要什么

Don'ts ❌

  1. 模糊不清:避免模棱两可的表达
  2. 过度复杂:一次性要求太多
  3. 缺少上下文:信息不足
  4. 忽略格式:没有结构化输出
  5. 一成不变:不测试不优化
  6. 忽视token限制:超出上下文窗口
  7. 缺少验证:不检查输出质量
  8. 滥用情感:不当的情感引导

🎓 实战案例

案例1:代码Review助手

CODE_REVIEW_PROMPT = """
你是一位资深的{language}工程师,有15年开发经验。

请review以下代码:

```{language}
{code}

请从以下维度分析:

  1. 代码质量(1-10分)

    • 可读性
    • 可维护性
    • 代码规范
  2. 潜在问题

    • Bug风险
    • 性能问题
    • 安全隐患
  3. 优化建议

    • 具体改进代码
    • 解释优化理由
  4. 最佳实践

    • 是否遵循最佳实践
    • 推荐的设计模式

格式要求:

  • 使用Markdown格式
  • 代码示例使用代码块
  • 每个问题给出严重程度(🔴严重/🟡中等/🟢轻微)

开始review: """

使用

review = llm.generate(CODE_REVIEW_PROMPT.format( language="Python", code=user_code ))


### 案例2:智能客服

```python
CUSTOMER_SERVICE_PROMPT = """
你是{company_name}的客服代表,友好、专业、高效。

公司信息:
- 主营业务:{business}
- 服务时间:{service_hours}
- 退换货政策:{return_policy}

常见问题库:
{faq}

对话历史:
{chat_history}

客户最新问题:
{customer_question}

请回答客户问题,注意:
1. 语气友好亲切
2. 如果问题在FAQ中,直接回答
3. 如果需要人工处理,引导转人工
4. 必要时询问补充信息
5. 回答要具体,避免模糊

你的回复:
"""

案例3:文档问答系统

QA_WITH_CONTEXT_PROMPT = """
基于以下文档内容回答问题。

文档内容:
\"\"\"
{context}
\"\"\"

问题:{question}

回答要求:
1. 只基于文档内容回答
2. 如果文档中没有相关信息,明确说明"文档中未找到相关信息"
3. 引用具体的段落或章节
4. 提供简洁但完整的答案

回答:
"""

# 使用RAG
def answer_with_rag(question: str, vector_store) -> str:
    # 检索相关文档
    relevant_docs = vector_store.search(question, k=3)
    
    # 构建上下文
    context = "\n\n---\n\n".join([doc.content for doc in relevant_docs])
    
    # 生成答案
    prompt = QA_WITH_CONTEXT_PROMPT.format(
        context=context,
        question=question
    )
    
    answer = llm.generate(prompt)
    
    # 附加来源
    sources = [doc.metadata['source'] for doc in relevant_docs]
    answer += f"\n\n来源:{', '.join(sources)}"
    
    return answer

📚 参考资源

学习资源

  • OpenAI Prompt Engineering Guide
  • Anthropic Prompt Engineering
  • Learn Prompting (learnprompting.org)
  • Prompt Engineering Guide (promptingguide.ai)

工具推荐

  • ChatGPT Playground
  • Claude.ai
  • PromptPerfect
  • LangChain PromptTemplate

社区

  • r/PromptEngineering
  • PromptHub
  • ShareGPT

🔗 相关文章

  • 00-AI应用架构总体概述
  • 02-RAG系统架构与实践
  • 03-Agent系统设计与实现

最后更新:2024年12月22日

最近更新: 2025/12/22 14:25
Contributors: wsyx