# QA Generation CN - 中文问答对生成工具
一个强大的中文文档问答对(QA pairs)自动生成和验证工具,支持多种LLM提供商,具备完善的质量验证机制。
## ✨ 功能特性
- 🤖 **多LLM支持**: 支持Ollama(本地)和OpenAI(云端)模型
- 📄 **智能文档处理**: 自动分块、中文优化处理
- ✅ **多维度验证**: 语义相似度、关键词匹配、长度控制、唯一性检测
- 📊 **详细统计**: 生成质量报告和数据分析
- 🎯 **中文优化**: 专门针对中文内容优化
- 🔧 **灵活配置**: 丰富的参数配置选项
## 🚀 快速开始
### 1. 环境准备
```bash
# 克隆项目
git clone <repository-url>
cd qa_gen_cn
# 安装依赖
pip install -r requirements.txt
# 激活conda环境(如果使用)
conda activate LLM
```
### 2. 配置LLM
#### 使用Ollama(推荐,本地运行)
```bash
# 安装Ollama
curl -fsSL https://ollama.ai/install.sh | sh
# 启动Ollama服务
ollama serve
# 下载模型
ollama pull llama3.1:8b
# 或下载其他模型
ollama pull qwen3:8b
ollama pull gemma2:9b
```
#### 使用OpenAI(云端)
```bash
# 设置API密钥
export OPENAI_API_KEY="your-api-key-here"
```
### 3. 基础使用
#### 方法一:使用完整脚本(推荐)
```bash
# 运行完整的生成和验证流程
python examples/generate_and_validate_qa.py
```
#### 方法二:使用简化脚本
```bash
# 仅生成QA pairs,不进行验证
python examples/generator_and_no_validate_qa.py
```
#### 方法三:编程方式使用
```python
from qa_gen_cn import generate_qa_pairs
# 基础使用
qa_pairs = generate_qa_pairs(
doc_path="your_document.txt",
llm_provider="ollama",
llm_model="llama3.1:8b"
)
# 自定义配置
qa_pairs = generate_qa_pairs(
doc_path="your_document.txt",
llm_provider="openai",
llm_model="gpt-3.5-turbo",
show_chunks=True,
validation_config={
"keyword_top_n": 10
},
api_key="your-openai-api-key"
)
```
## 📖 详细使用指南
### 1. 文档格式要求
支持纯文本文件(.txt),内容示例:
```text
大有唐王降敕封,钦差玄奘问禅宗。坚心磨琢寻龙穴,着意修持上鹫峰。
边界远游多少国,云山前度万千重。自今别驾投西去,秉教迦持悟大空。
却说三藏自贞观十三年九月望前三日,蒙唐王与多官送出长安关外。
一二日马不停蹄,早至法门寺。本寺住持上房长老,带领众僧有五百余人,
两边罗列,接至里面,相见献茶。茶罢进斋。斋后不觉天晚。
```
### 2. 配置参数详解
#### LLM配置
```python
# Ollama配置
llm_config = {
"llm_provider": "ollama",
"llm_model": "llama3.1:8b", # 或其他可用模型
"show_chunks": True, # 显示文档分块过程
"chunk_size": 500, # 文档块大小
"chunk_overlap": 50 # 块重叠大小
}
# OpenAI配置
openai_config = {
"llm_provider": "openai",
"llm_model": "gpt-3.5-turbo", # 或 "gpt-4"
"api_key": "your-api-key"
}
```
#### 验证配置
```python
validation_config = {
# 语义相似度验证
"similarity_threshold": 0.3, # 相似度阈值(0-1)
"similarity_model": "paraphrase-multilingual-MiniLM-L12-v2",
}
```
### 3. 高级使用示例
#### 自定义生成流程
```python
from qa_gen_cn.generator import QAGenerator
from qa_gen_cn.llm_factory import LLMFactory
from qa_gen_cn.validator import QAPairValidator
from qa_gen_cn.utils import load_document
# 1. 初始化LLM
llm = LLMFactory.create_llm(
provider='ollama',
model='llama3.1:8b',
temperature=0.7
)
# 2. 创建生成器
generator = QAGenerator(llm=llm, show_chunks=True)
# 3. 生成QA pairs
qa_pairs = generator.generate_from_document(
doc_path="your_document.txt",
chunk_size=3000,
chunk_overlap=100
)
# 4. 配置验证器
validator = QAPairValidator({
"similarity_threshold": 0.4,
'similarity_model':'paraphrase-multilingual-MiniLM-L12-v2'
})
# 5. 验证QA pairs
doc_content = " ".join([doc.page_content for doc in load_document("your_document.txt")])
validated_pairs = validator.validate(qa_pairs, doc_content)
print(f"生成 {len(qa_pairs)} 个QA pairs,验证通过 {len(validated_pairs)} 个")
```
## 📊 输出结果
### 文件结构
运行完成后,会在`output`目录生成以下文件:
```
output/
├── qa_generation_result.json # 完整结果(包含配置、统计等)
├── qa_pairs.json # 纯QA pairs数据
└── statistics.txt # 统计报告
```
### 输出格式示例
#### QA Pairs JSON格式
```json
[
{
"question": "什么是人工智能?",
"answer": "人工智能是计算机科学的一个分支,旨在创建能够模拟人类智能的机器。"
},
{
"question": "机器学习和深度学习的关系是什么?",
"answer": "机器学习是人工智能的分支,深度学习是机器学习的子集,使用神经网络进行学习。"
}
]
```
#### 统计报告示例
```
=== QA Pairs 生成和验证统计报告 ===
文档路径: examples/1.txt
LLM配置: {'provider': 'ollama', 'model': 'llama3.1:8b'}
统计信息:
- 总生成数量: 25
- 验证通过数量: 18
- 验证通过率: 72.00%
- 平均问题长度: 23.4 字符
- 平均答案长度: 156.7 字符
验证配置:
- keyword_top_n: 15
```
## 🔧 验证机制详解
### 1. 语义相似度验证
- **原理**: 使用多语言语义模型计算问题、答案与原文的相似度
- **作用**: 确保生成的QA pairs与原文内容相关
- **配置**: `similarity_threshold` (0-1,越高越严格),`similarity_model`
### 2. 关键词匹配验证
- **原理**: 提取原文关键词,验证问题和答案是否包含相关关键词
- **作用**: 保证QA pairs涵盖文档核心内容
- **配置**: `keyword_top_n` (提取关键词数量)
### 3. 长度验证
- **原理**: 检查问题和答案的长度是否在合理范围内
- **作用**: 避免过短或过长的QA pairs
- **配置**: `question_min_length`,`question_max_length`,`answer_min_length`, `answer_max_length`
### 4. 唯一性验证
- **原理**: 使用聚类算法检测重复的QA pairs
- **作用**: 确保生成结果的多样性
- **配置**: `similarity_model`,`uniqueness_check_enabled`,`uniqueness_distance_threshold` (聚类距离阈值),越小越好(更严格去重),但需要根据你的具体需求来平衡数量和质量。
- 0.0: 理论上不允许任何重复,但实际中很少使用
- 1.0: 允许所有内容,相当于关闭去重功能
- 建议范围: 0.05-0.3 之间,根据具体需求调整
### 5. 特别注意
Validation 1,2,3,4 validation是互斥的,只能选择一个验证
验证优先级:**1>2>3>4**,在self.config中配置了:
1 similarity_threshold和similarity_model,后面其他验证的配置可以不配置,如果配置了也不起作用。
2 question_min_length和question_max_length,answer_min_length和answer_max_length,后面其他验证的配置可以不配置,如果配置了也不起作用。
3 keyword_top_n,后面其他验证的配置可以不配置,如果配置了也不起作用。
4 similarity_model、uniqueness_distance_threshold和uniqueness_check_enabled,其他验证的配置可以不配置,如果配置了也不起作用。
## 🛠️ 故障排除
### 常见问题及解决方案
#### 1. Ollama连接问题
```bash
# 检查Ollama服务状态
ollama list
# 重启Ollama服务
ollama serve
# 检查模型是否已下载
ollama show llama3.1:8b
```
#### 2. OpenAI API问题
```bash
# 检查API密钥
echo $OPENAI_API_KEY
# 测试API连接
curl -H "Authorization: Bearer $OPENAI_API_KEY" \
https://api.openai.com/v1/models
```
#### 3. 验证失败率高
```python
# 降低验证标准
validation_config = {
"similarity_threshold": 0.1, # 降低相似度要求
}
```
#### 4. 内存不足
```python
# 减小处理块大小
config = {
"chunk_size": 2000, # 减小块大小
"chunk_overlap": 100 # 减小重叠
}
```
### 调试模式
启用详细输出查看处理过程:
```python
# 显示文档分块
"show_chunks": True
# 查看验证详情
validator = QAPairValidator(config)
# 可以单独测试各个验证方法
```
## 🧪 测试
运行单元测试确保功能正常:
```bash
# 运行所有测试
python -m pytest tests/ -v
# 运行特定测试
python -m pytest tests/test_generator.py -v
# 运行覆盖率测试
python -m pytest tests/ --cov=qa_gen_cn --cov-report=html
```
## 📁 项目结构
```
qa_gen_cn/
├── qa_gen_cn/ # 核心模块
│ ├── __init__.py # 主入口
│ ├── generator.py # QA生成器
│ ├── llm_factory.py # LLM工厂
│ ├── validator.py # 验证器
│ ├── super_json.py # JSON处理工具
│ └── utils.py # 工具函数
├── examples/ # 示例代码
│ ├── generate_and_validate_qa.py # 完整生成脚本
│ ├── generator_and_no_validate_qa.py # 简化生成脚本
│ └── 1.txt # 示例文档
├── tests/ # 单元测试
│ ├── test_generator.py
│ ├── test_validator.py
│ └── ...
├── output/ # 输出目录
├── requirements.txt # 依赖列表
├── pyproject.toml # 项目配置
└── README.md # 本文档
```
## 🛠️ 技术栈
- **LangChain**: LLM集成和链式处理
- **Sentence Transformers**: 语义相似度计算
- **jieba**: 中文分词和关键词提取
- **scikit-learn**: 聚类和去重算法
- **Ollama**: 本地LLM服务
- **OpenAI**: 云端LLM API
- **pytest**: 单元测试框架
## 📄 许可证
本项目基于MIT许可证开源。
## 🤝 贡献
欢迎提交Issue和Pull Request来改进这个项目!
## 📞 支持
如果遇到问题,请:
1. 查看本文档的故障排除部分
2. 检查项目的Issues页面
3. 提交新的Issue描述问题
Raw data
{
"_id": null,
"home_page": null,
"name": "qagen",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.9",
"maintainer_email": null,
"keywords": "ai, chinese, document-processing, llm, nlp, qa-generation",
"author": null,
"author_email": "CrissChan <can101208@gmail.com>",
"download_url": "https://files.pythonhosted.org/packages/27/15/9956402267ff1944eee3cb15e9d21c8d283123c03a879f9427497231c9ba/qagen-0.1.1.tar.gz",
"platform": null,
"description": "# QA Generation CN - \u4e2d\u6587\u95ee\u7b54\u5bf9\u751f\u6210\u5de5\u5177\n\n\u4e00\u4e2a\u5f3a\u5927\u7684\u4e2d\u6587\u6587\u6863\u95ee\u7b54\u5bf9\uff08QA pairs\uff09\u81ea\u52a8\u751f\u6210\u548c\u9a8c\u8bc1\u5de5\u5177\uff0c\u652f\u6301\u591a\u79cdLLM\u63d0\u4f9b\u5546\uff0c\u5177\u5907\u5b8c\u5584\u7684\u8d28\u91cf\u9a8c\u8bc1\u673a\u5236\u3002\n\n## \u2728 \u529f\u80fd\u7279\u6027\n\n- \ud83e\udd16 **\u591aLLM\u652f\u6301**: \u652f\u6301Ollama\uff08\u672c\u5730\uff09\u548cOpenAI\uff08\u4e91\u7aef\uff09\u6a21\u578b\n- \ud83d\udcc4 **\u667a\u80fd\u6587\u6863\u5904\u7406**: \u81ea\u52a8\u5206\u5757\u3001\u4e2d\u6587\u4f18\u5316\u5904\u7406\n- \u2705 **\u591a\u7ef4\u5ea6\u9a8c\u8bc1**: \u8bed\u4e49\u76f8\u4f3c\u5ea6\u3001\u5173\u952e\u8bcd\u5339\u914d\u3001\u957f\u5ea6\u63a7\u5236\u3001\u552f\u4e00\u6027\u68c0\u6d4b\n- \ud83d\udcca **\u8be6\u7ec6\u7edf\u8ba1**: \u751f\u6210\u8d28\u91cf\u62a5\u544a\u548c\u6570\u636e\u5206\u6790\n- \ud83c\udfaf **\u4e2d\u6587\u4f18\u5316**: \u4e13\u95e8\u9488\u5bf9\u4e2d\u6587\u5185\u5bb9\u4f18\u5316\n- \ud83d\udd27 **\u7075\u6d3b\u914d\u7f6e**: \u4e30\u5bcc\u7684\u53c2\u6570\u914d\u7f6e\u9009\u9879\n\n## \ud83d\ude80 \u5feb\u901f\u5f00\u59cb\n\n### 1. \u73af\u5883\u51c6\u5907\n\n```bash\n# \u514b\u9686\u9879\u76ee\ngit clone <repository-url>\ncd qa_gen_cn\n\n# \u5b89\u88c5\u4f9d\u8d56\npip install -r requirements.txt\n\n# \u6fc0\u6d3bconda\u73af\u5883\uff08\u5982\u679c\u4f7f\u7528\uff09\nconda activate LLM\n```\n\n### 2. \u914d\u7f6eLLM\n\n#### \u4f7f\u7528Ollama\uff08\u63a8\u8350\uff0c\u672c\u5730\u8fd0\u884c\uff09\n\n```bash\n# \u5b89\u88c5Ollama\ncurl -fsSL https://ollama.ai/install.sh | sh\n\n# \u542f\u52a8Ollama\u670d\u52a1\nollama serve\n\n# \u4e0b\u8f7d\u6a21\u578b\nollama pull llama3.1:8b\n# \u6216\u4e0b\u8f7d\u5176\u4ed6\u6a21\u578b\nollama pull qwen3:8b\nollama pull gemma2:9b\n```\n\n#### \u4f7f\u7528OpenAI\uff08\u4e91\u7aef\uff09\n\n```bash\n# \u8bbe\u7f6eAPI\u5bc6\u94a5\nexport OPENAI_API_KEY=\"your-api-key-here\"\n```\n\n### 3. \u57fa\u7840\u4f7f\u7528\n\n#### \u65b9\u6cd5\u4e00\uff1a\u4f7f\u7528\u5b8c\u6574\u811a\u672c\uff08\u63a8\u8350\uff09\n\n```bash\n# \u8fd0\u884c\u5b8c\u6574\u7684\u751f\u6210\u548c\u9a8c\u8bc1\u6d41\u7a0b\npython examples/generate_and_validate_qa.py\n```\n\n#### \u65b9\u6cd5\u4e8c\uff1a\u4f7f\u7528\u7b80\u5316\u811a\u672c\n\n```bash\n# \u4ec5\u751f\u6210QA pairs\uff0c\u4e0d\u8fdb\u884c\u9a8c\u8bc1\npython examples/generator_and_no_validate_qa.py\n```\n\n#### \u65b9\u6cd5\u4e09\uff1a\u7f16\u7a0b\u65b9\u5f0f\u4f7f\u7528\n\n```python\nfrom qa_gen_cn import generate_qa_pairs\n\n# \u57fa\u7840\u4f7f\u7528\nqa_pairs = generate_qa_pairs(\n doc_path=\"your_document.txt\",\n llm_provider=\"ollama\",\n llm_model=\"llama3.1:8b\"\n)\n\n# \u81ea\u5b9a\u4e49\u914d\u7f6e\nqa_pairs = generate_qa_pairs(\n doc_path=\"your_document.txt\",\n llm_provider=\"openai\",\n llm_model=\"gpt-3.5-turbo\",\n show_chunks=True,\n validation_config={\n \"keyword_top_n\": 10\n },\n api_key=\"your-openai-api-key\"\n)\n```\n\n## \ud83d\udcd6 \u8be6\u7ec6\u4f7f\u7528\u6307\u5357\n\n### 1. \u6587\u6863\u683c\u5f0f\u8981\u6c42\n\n\u652f\u6301\u7eaf\u6587\u672c\u6587\u4ef6\uff08.txt\uff09\uff0c\u5185\u5bb9\u793a\u4f8b\uff1a\n\n```text\n\u5927\u6709\u5510\u738b\u964d\u6555\u5c01\uff0c\u94a6\u5dee\u7384\u5958\u95ee\u7985\u5b97\u3002\u575a\u5fc3\u78e8\u7422\u5bfb\u9f99\u7a74\uff0c\u7740\u610f\u4fee\u6301\u4e0a\u9e6b\u5cf0\u3002\n\u8fb9\u754c\u8fdc\u6e38\u591a\u5c11\u56fd\uff0c\u4e91\u5c71\u524d\u5ea6\u4e07\u5343\u91cd\u3002\u81ea\u4eca\u522b\u9a7e\u6295\u897f\u53bb\uff0c\u79c9\u6559\u8fe6\u6301\u609f\u5927\u7a7a\u3002\n\n\u5374\u8bf4\u4e09\u85cf\u81ea\u8d1e\u89c2\u5341\u4e09\u5e74\u4e5d\u6708\u671b\u524d\u4e09\u65e5\uff0c\u8499\u5510\u738b\u4e0e\u591a\u5b98\u9001\u51fa\u957f\u5b89\u5173\u5916\u3002\n\u4e00\u4e8c\u65e5\u9a6c\u4e0d\u505c\u8e44\uff0c\u65e9\u81f3\u6cd5\u95e8\u5bfa\u3002\u672c\u5bfa\u4f4f\u6301\u4e0a\u623f\u957f\u8001\uff0c\u5e26\u9886\u4f17\u50e7\u6709\u4e94\u767e\u4f59\u4eba\uff0c\n\u4e24\u8fb9\u7f57\u5217\uff0c\u63a5\u81f3\u91cc\u9762\uff0c\u76f8\u89c1\u732e\u8336\u3002\u8336\u7f62\u8fdb\u658b\u3002\u658b\u540e\u4e0d\u89c9\u5929\u665a\u3002\n```\n\n### 2. \u914d\u7f6e\u53c2\u6570\u8be6\u89e3\n\n#### LLM\u914d\u7f6e\n\n```python\n# Ollama\u914d\u7f6e\nllm_config = {\n \"llm_provider\": \"ollama\",\n \"llm_model\": \"llama3.1:8b\", # \u6216\u5176\u4ed6\u53ef\u7528\u6a21\u578b\n \"show_chunks\": True, # \u663e\u793a\u6587\u6863\u5206\u5757\u8fc7\u7a0b\n \"chunk_size\": 500, # \u6587\u6863\u5757\u5927\u5c0f\n \"chunk_overlap\": 50 # \u5757\u91cd\u53e0\u5927\u5c0f\n}\n\n# OpenAI\u914d\u7f6e\nopenai_config = {\n \"llm_provider\": \"openai\",\n \"llm_model\": \"gpt-3.5-turbo\", # \u6216 \"gpt-4\"\n \"api_key\": \"your-api-key\"\n}\n```\n\n#### \u9a8c\u8bc1\u914d\u7f6e\n\n```python\nvalidation_config = {\n # \u8bed\u4e49\u76f8\u4f3c\u5ea6\u9a8c\u8bc1\n \"similarity_threshold\": 0.3, # \u76f8\u4f3c\u5ea6\u9608\u503c\uff080-1\uff09\n \"similarity_model\": \"paraphrase-multilingual-MiniLM-L12-v2\",\n \n}\n```\n\n### 3. \u9ad8\u7ea7\u4f7f\u7528\u793a\u4f8b\n\n#### \u81ea\u5b9a\u4e49\u751f\u6210\u6d41\u7a0b\n\n```python\nfrom qa_gen_cn.generator import QAGenerator\nfrom qa_gen_cn.llm_factory import LLMFactory\nfrom qa_gen_cn.validator import QAPairValidator\nfrom qa_gen_cn.utils import load_document\n\n# 1. \u521d\u59cb\u5316LLM\nllm = LLMFactory.create_llm(\n provider='ollama', \n model='llama3.1:8b',\n temperature=0.7\n)\n\n# 2. \u521b\u5efa\u751f\u6210\u5668\ngenerator = QAGenerator(llm=llm, show_chunks=True)\n\n# 3. \u751f\u6210QA pairs\nqa_pairs = generator.generate_from_document(\n doc_path=\"your_document.txt\",\n chunk_size=3000,\n chunk_overlap=100\n)\n\n# 4. \u914d\u7f6e\u9a8c\u8bc1\u5668\nvalidator = QAPairValidator({\n \"similarity_threshold\": 0.4,\n 'similarity_model':'paraphrase-multilingual-MiniLM-L12-v2'\n})\n\n# 5. \u9a8c\u8bc1QA pairs\ndoc_content = \" \".join([doc.page_content for doc in load_document(\"your_document.txt\")])\nvalidated_pairs = validator.validate(qa_pairs, doc_content)\n\nprint(f\"\u751f\u6210 {len(qa_pairs)} \u4e2aQA pairs\uff0c\u9a8c\u8bc1\u901a\u8fc7 {len(validated_pairs)} \u4e2a\")\n```\n\n\n\n## \ud83d\udcca \u8f93\u51fa\u7ed3\u679c\n\n### \u6587\u4ef6\u7ed3\u6784\n\n\u8fd0\u884c\u5b8c\u6210\u540e\uff0c\u4f1a\u5728`output`\u76ee\u5f55\u751f\u6210\u4ee5\u4e0b\u6587\u4ef6\uff1a\n\n```\noutput/\n\u251c\u2500\u2500 qa_generation_result.json # \u5b8c\u6574\u7ed3\u679c\uff08\u5305\u542b\u914d\u7f6e\u3001\u7edf\u8ba1\u7b49\uff09\n\u251c\u2500\u2500 qa_pairs.json # \u7eafQA pairs\u6570\u636e\n\u2514\u2500\u2500 statistics.txt # \u7edf\u8ba1\u62a5\u544a\n```\n\n### \u8f93\u51fa\u683c\u5f0f\u793a\u4f8b\n\n#### QA Pairs JSON\u683c\u5f0f\n\n```json\n[\n {\n \"question\": \"\u4ec0\u4e48\u662f\u4eba\u5de5\u667a\u80fd\uff1f\",\n \"answer\": \"\u4eba\u5de5\u667a\u80fd\u662f\u8ba1\u7b97\u673a\u79d1\u5b66\u7684\u4e00\u4e2a\u5206\u652f\uff0c\u65e8\u5728\u521b\u5efa\u80fd\u591f\u6a21\u62df\u4eba\u7c7b\u667a\u80fd\u7684\u673a\u5668\u3002\"\n },\n {\n \"question\": \"\u673a\u5668\u5b66\u4e60\u548c\u6df1\u5ea6\u5b66\u4e60\u7684\u5173\u7cfb\u662f\u4ec0\u4e48\uff1f\",\n \"answer\": \"\u673a\u5668\u5b66\u4e60\u662f\u4eba\u5de5\u667a\u80fd\u7684\u5206\u652f\uff0c\u6df1\u5ea6\u5b66\u4e60\u662f\u673a\u5668\u5b66\u4e60\u7684\u5b50\u96c6\uff0c\u4f7f\u7528\u795e\u7ecf\u7f51\u7edc\u8fdb\u884c\u5b66\u4e60\u3002\"\n }\n]\n```\n\n#### \u7edf\u8ba1\u62a5\u544a\u793a\u4f8b\n\n```\n=== QA Pairs \u751f\u6210\u548c\u9a8c\u8bc1\u7edf\u8ba1\u62a5\u544a ===\n\n\u6587\u6863\u8def\u5f84: examples/1.txt\nLLM\u914d\u7f6e: {'provider': 'ollama', 'model': 'llama3.1:8b'}\n\n\u7edf\u8ba1\u4fe1\u606f:\n- \u603b\u751f\u6210\u6570\u91cf: 25\n- \u9a8c\u8bc1\u901a\u8fc7\u6570\u91cf: 18\n- \u9a8c\u8bc1\u901a\u8fc7\u7387: 72.00%\n- \u5e73\u5747\u95ee\u9898\u957f\u5ea6: 23.4 \u5b57\u7b26\n- \u5e73\u5747\u7b54\u6848\u957f\u5ea6: 156.7 \u5b57\u7b26\n\n\u9a8c\u8bc1\u914d\u7f6e:\n- keyword_top_n: 15\n```\n\n## \ud83d\udd27 \u9a8c\u8bc1\u673a\u5236\u8be6\u89e3\n\n### 1. \u8bed\u4e49\u76f8\u4f3c\u5ea6\u9a8c\u8bc1\n- **\u539f\u7406**: \u4f7f\u7528\u591a\u8bed\u8a00\u8bed\u4e49\u6a21\u578b\u8ba1\u7b97\u95ee\u9898\u3001\u7b54\u6848\u4e0e\u539f\u6587\u7684\u76f8\u4f3c\u5ea6\n- **\u4f5c\u7528**: \u786e\u4fdd\u751f\u6210\u7684QA pairs\u4e0e\u539f\u6587\u5185\u5bb9\u76f8\u5173\n- **\u914d\u7f6e**: `similarity_threshold` (0-1\uff0c\u8d8a\u9ad8\u8d8a\u4e25\u683c),`similarity_model`\n\n### 2. \u5173\u952e\u8bcd\u5339\u914d\u9a8c\u8bc1\n- **\u539f\u7406**: \u63d0\u53d6\u539f\u6587\u5173\u952e\u8bcd\uff0c\u9a8c\u8bc1\u95ee\u9898\u548c\u7b54\u6848\u662f\u5426\u5305\u542b\u76f8\u5173\u5173\u952e\u8bcd\n- **\u4f5c\u7528**: \u4fdd\u8bc1QA pairs\u6db5\u76d6\u6587\u6863\u6838\u5fc3\u5185\u5bb9\n- **\u914d\u7f6e**: `keyword_top_n` (\u63d0\u53d6\u5173\u952e\u8bcd\u6570\u91cf)\n\n### 3. \u957f\u5ea6\u9a8c\u8bc1\n- **\u539f\u7406**: \u68c0\u67e5\u95ee\u9898\u548c\u7b54\u6848\u7684\u957f\u5ea6\u662f\u5426\u5728\u5408\u7406\u8303\u56f4\u5185\n- **\u4f5c\u7528**: \u907f\u514d\u8fc7\u77ed\u6216\u8fc7\u957f\u7684QA pairs\n- **\u914d\u7f6e**: `question_min_length`,`question_max_length`,`answer_min_length`, `answer_max_length`\n\n### 4. \u552f\u4e00\u6027\u9a8c\u8bc1\n- **\u539f\u7406**: \u4f7f\u7528\u805a\u7c7b\u7b97\u6cd5\u68c0\u6d4b\u91cd\u590d\u7684QA pairs\n- **\u4f5c\u7528**: \u786e\u4fdd\u751f\u6210\u7ed3\u679c\u7684\u591a\u6837\u6027\n- **\u914d\u7f6e**: `similarity_model`,`uniqueness_check_enabled`,`uniqueness_distance_threshold` (\u805a\u7c7b\u8ddd\u79bb\u9608\u503c)\uff0c\u8d8a\u5c0f\u8d8a\u597d\uff08\u66f4\u4e25\u683c\u53bb\u91cd\uff09\uff0c\u4f46\u9700\u8981\u6839\u636e\u4f60\u7684\u5177\u4f53\u9700\u6c42\u6765\u5e73\u8861\u6570\u91cf\u548c\u8d28\u91cf\u3002\n - 0.0: \u7406\u8bba\u4e0a\u4e0d\u5141\u8bb8\u4efb\u4f55\u91cd\u590d\uff0c\u4f46\u5b9e\u9645\u4e2d\u5f88\u5c11\u4f7f\u7528\n - 1.0: \u5141\u8bb8\u6240\u6709\u5185\u5bb9\uff0c\u76f8\u5f53\u4e8e\u5173\u95ed\u53bb\u91cd\u529f\u80fd\n - \u5efa\u8bae\u8303\u56f4: 0.05-0.3 \u4e4b\u95f4\uff0c\u6839\u636e\u5177\u4f53\u9700\u6c42\u8c03\u6574\n\n\n### 5. \u7279\u522b\u6ce8\u610f\nValidation 1,2,3,4 validation\u662f\u4e92\u65a5\u7684\uff0c\u53ea\u80fd\u9009\u62e9\u4e00\u4e2a\u9a8c\u8bc1\n\u9a8c\u8bc1\u4f18\u5148\u7ea7\uff1a**1>2>3>4**\uff0c\u5728self.config\u4e2d\u914d\u7f6e\u4e86\uff1a\n 1 similarity_threshold\u548csimilarity_model\uff0c\u540e\u9762\u5176\u4ed6\u9a8c\u8bc1\u7684\u914d\u7f6e\u53ef\u4ee5\u4e0d\u914d\u7f6e\uff0c\u5982\u679c\u914d\u7f6e\u4e86\u4e5f\u4e0d\u8d77\u4f5c\u7528\u3002\n 2 question_min_length\u548cquestion_max_length\uff0canswer_min_length\u548canswer_max_length\uff0c\u540e\u9762\u5176\u4ed6\u9a8c\u8bc1\u7684\u914d\u7f6e\u53ef\u4ee5\u4e0d\u914d\u7f6e\uff0c\u5982\u679c\u914d\u7f6e\u4e86\u4e5f\u4e0d\u8d77\u4f5c\u7528\u3002\n 3 keyword_top_n\uff0c\u540e\u9762\u5176\u4ed6\u9a8c\u8bc1\u7684\u914d\u7f6e\u53ef\u4ee5\u4e0d\u914d\u7f6e\uff0c\u5982\u679c\u914d\u7f6e\u4e86\u4e5f\u4e0d\u8d77\u4f5c\u7528\u3002\n 4 similarity_model\u3001uniqueness_distance_threshold\u548cuniqueness_check_enabled\uff0c\u5176\u4ed6\u9a8c\u8bc1\u7684\u914d\u7f6e\u53ef\u4ee5\u4e0d\u914d\u7f6e\uff0c\u5982\u679c\u914d\u7f6e\u4e86\u4e5f\u4e0d\u8d77\u4f5c\u7528\u3002\n## \ud83d\udee0\ufe0f \u6545\u969c\u6392\u9664\n\n### \u5e38\u89c1\u95ee\u9898\u53ca\u89e3\u51b3\u65b9\u6848\n\n#### 1. Ollama\u8fde\u63a5\u95ee\u9898\n\n```bash\n# \u68c0\u67e5Ollama\u670d\u52a1\u72b6\u6001\nollama list\n\n# \u91cd\u542fOllama\u670d\u52a1\nollama serve\n\n# \u68c0\u67e5\u6a21\u578b\u662f\u5426\u5df2\u4e0b\u8f7d\nollama show llama3.1:8b\n```\n\n#### 2. OpenAI API\u95ee\u9898\n\n```bash\n# \u68c0\u67e5API\u5bc6\u94a5\necho $OPENAI_API_KEY\n\n# \u6d4b\u8bd5API\u8fde\u63a5\ncurl -H \"Authorization: Bearer $OPENAI_API_KEY\" \\\n https://api.openai.com/v1/models\n```\n\n#### 3. \u9a8c\u8bc1\u5931\u8d25\u7387\u9ad8\n\n```python\n# \u964d\u4f4e\u9a8c\u8bc1\u6807\u51c6\nvalidation_config = {\n \"similarity_threshold\": 0.1, # \u964d\u4f4e\u76f8\u4f3c\u5ea6\u8981\u6c42\n}\n```\n\n#### 4. \u5185\u5b58\u4e0d\u8db3\n\n```python\n# \u51cf\u5c0f\u5904\u7406\u5757\u5927\u5c0f\nconfig = {\n \"chunk_size\": 2000, # \u51cf\u5c0f\u5757\u5927\u5c0f\n \"chunk_overlap\": 100 # \u51cf\u5c0f\u91cd\u53e0\n}\n```\n\n### \u8c03\u8bd5\u6a21\u5f0f\n\n\u542f\u7528\u8be6\u7ec6\u8f93\u51fa\u67e5\u770b\u5904\u7406\u8fc7\u7a0b\uff1a\n\n```python\n# \u663e\u793a\u6587\u6863\u5206\u5757\n\"show_chunks\": True\n\n# \u67e5\u770b\u9a8c\u8bc1\u8be6\u60c5\nvalidator = QAPairValidator(config)\n# \u53ef\u4ee5\u5355\u72ec\u6d4b\u8bd5\u5404\u4e2a\u9a8c\u8bc1\u65b9\u6cd5\n```\n\n## \ud83e\uddea \u6d4b\u8bd5\n\n\u8fd0\u884c\u5355\u5143\u6d4b\u8bd5\u786e\u4fdd\u529f\u80fd\u6b63\u5e38\uff1a\n\n```bash\n# \u8fd0\u884c\u6240\u6709\u6d4b\u8bd5\npython -m pytest tests/ -v\n\n# \u8fd0\u884c\u7279\u5b9a\u6d4b\u8bd5\npython -m pytest tests/test_generator.py -v\n\n# \u8fd0\u884c\u8986\u76d6\u7387\u6d4b\u8bd5\npython -m pytest tests/ --cov=qa_gen_cn --cov-report=html\n```\n\n## \ud83d\udcc1 \u9879\u76ee\u7ed3\u6784\n\n```\nqa_gen_cn/\n\u251c\u2500\u2500 qa_gen_cn/ # \u6838\u5fc3\u6a21\u5757\n\u2502 \u251c\u2500\u2500 __init__.py # \u4e3b\u5165\u53e3\n\u2502 \u251c\u2500\u2500 generator.py # QA\u751f\u6210\u5668\n\u2502 \u251c\u2500\u2500 llm_factory.py # LLM\u5de5\u5382\n\u2502 \u251c\u2500\u2500 validator.py # \u9a8c\u8bc1\u5668\n\u2502 \u251c\u2500\u2500 super_json.py # JSON\u5904\u7406\u5de5\u5177\n\u2502 \u2514\u2500\u2500 utils.py # \u5de5\u5177\u51fd\u6570\n\u251c\u2500\u2500 examples/ # \u793a\u4f8b\u4ee3\u7801\n\u2502 \u251c\u2500\u2500 generate_and_validate_qa.py # \u5b8c\u6574\u751f\u6210\u811a\u672c\n\u2502 \u251c\u2500\u2500 generator_and_no_validate_qa.py # \u7b80\u5316\u751f\u6210\u811a\u672c\n\u2502 \u2514\u2500\u2500 1.txt # \u793a\u4f8b\u6587\u6863\n\u251c\u2500\u2500 tests/ # \u5355\u5143\u6d4b\u8bd5\n\u2502 \u251c\u2500\u2500 test_generator.py\n\u2502 \u251c\u2500\u2500 test_validator.py\n\u2502 \u2514\u2500\u2500 ...\n\u251c\u2500\u2500 output/ # \u8f93\u51fa\u76ee\u5f55\n\u251c\u2500\u2500 requirements.txt # \u4f9d\u8d56\u5217\u8868\n\u251c\u2500\u2500 pyproject.toml # \u9879\u76ee\u914d\u7f6e\n\u2514\u2500\u2500 README.md # \u672c\u6587\u6863\n```\n\n## \ud83d\udee0\ufe0f \u6280\u672f\u6808\n\n- **LangChain**: LLM\u96c6\u6210\u548c\u94fe\u5f0f\u5904\u7406\n- **Sentence Transformers**: \u8bed\u4e49\u76f8\u4f3c\u5ea6\u8ba1\u7b97\n- **jieba**: \u4e2d\u6587\u5206\u8bcd\u548c\u5173\u952e\u8bcd\u63d0\u53d6\n- **scikit-learn**: \u805a\u7c7b\u548c\u53bb\u91cd\u7b97\u6cd5\n- **Ollama**: \u672c\u5730LLM\u670d\u52a1\n- **OpenAI**: \u4e91\u7aefLLM API\n- **pytest**: \u5355\u5143\u6d4b\u8bd5\u6846\u67b6\n\n## \ud83d\udcc4 \u8bb8\u53ef\u8bc1\n\n\u672c\u9879\u76ee\u57fa\u4e8eMIT\u8bb8\u53ef\u8bc1\u5f00\u6e90\u3002\n\n## \ud83e\udd1d \u8d21\u732e\n\n\u6b22\u8fce\u63d0\u4ea4Issue\u548cPull Request\u6765\u6539\u8fdb\u8fd9\u4e2a\u9879\u76ee\uff01\n\n## \ud83d\udcde \u652f\u6301\n\n\u5982\u679c\u9047\u5230\u95ee\u9898\uff0c\u8bf7\uff1a\n1. \u67e5\u770b\u672c\u6587\u6863\u7684\u6545\u969c\u6392\u9664\u90e8\u5206\n2. \u68c0\u67e5\u9879\u76ee\u7684Issues\u9875\u9762\n3. \u63d0\u4ea4\u65b0\u7684Issue\u63cf\u8ff0\u95ee\u9898\n",
"bugtrack_url": null,
"license": "MIT",
"summary": "A powerful Chinese document QA pairs generation and validation tool with multiple LLM support",
"version": "0.1.1",
"project_urls": {
"Bug Tracker": "https://github.com/crisschan/qa-gen-cn/issues",
"Documentation": "https://github.com/crisschan/qa-gen-cn#readme",
"Homepage": "https://github.com/crisschan/qa-gen-cn",
"Repository": "https://github.com/crisschan/qa-gen-cn",
"Source Code": "https://github.com/crisschan/qa-gen-cn"
},
"split_keywords": [
"ai",
" chinese",
" document-processing",
" llm",
" nlp",
" qa-generation"
],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "f6a8b00ef40afb4d79ac6054fd33af6e6c5b1a65749f4596ffe1e3f38e3dc56e",
"md5": "ee84554dbf79ed3b737ec5f14ac6a518",
"sha256": "add6a9f2917d431a0eb14c77c22b28041828c09206a67b927d573c2579e0a827"
},
"downloads": -1,
"filename": "qagen-0.1.1-py3-none-any.whl",
"has_sig": false,
"md5_digest": "ee84554dbf79ed3b737ec5f14ac6a518",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.9",
"size": 15849,
"upload_time": "2025-08-21T10:17:32",
"upload_time_iso_8601": "2025-08-21T10:17:32.433271Z",
"url": "https://files.pythonhosted.org/packages/f6/a8/b00ef40afb4d79ac6054fd33af6e6c5b1a65749f4596ffe1e3f38e3dc56e/qagen-0.1.1-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "27159956402267ff1944eee3cb15e9d21c8d283123c03a879f9427497231c9ba",
"md5": "777735ccb15c7e9ecdef629cb8df54f3",
"sha256": "c51fd599cfbdb881d6a4ec2b17f805624fca096ad3805397f59f7179e0f141fe"
},
"downloads": -1,
"filename": "qagen-0.1.1.tar.gz",
"has_sig": false,
"md5_digest": "777735ccb15c7e9ecdef629cb8df54f3",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.9",
"size": 26304,
"upload_time": "2025-08-21T10:17:34",
"upload_time_iso_8601": "2025-08-21T10:17:34.615582Z",
"url": "https://files.pythonhosted.org/packages/27/15/9956402267ff1944eee3cb15e9d21c8d283123c03a879f9427497231c9ba/qagen-0.1.1.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-08-21 10:17:34",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "crisschan",
"github_project": "qa-gen-cn",
"travis_ci": false,
"coveralls": false,
"github_actions": false,
"requirements": [
{
"name": "langchain",
"specs": [
[
">=",
"0.1.0"
]
]
},
{
"name": "langchain-ollama",
"specs": [
[
">=",
"0.1.0"
]
]
},
{
"name": "langchain-openai",
"specs": [
[
">=",
"0.1.0"
]
]
},
{
"name": "langchain-community",
"specs": [
[
">=",
"0.1.0"
]
]
},
{
"name": "sentence-transformers",
"specs": [
[
">=",
"2.2.0"
]
]
},
{
"name": "jieba",
"specs": [
[
">=",
"0.42.1"
]
]
},
{
"name": "scikit-learn",
"specs": [
[
">=",
"1.3.0"
]
]
},
{
"name": "numpy",
"specs": [
[
"<",
"2.0"
]
]
},
{
"name": "torch",
"specs": [
[
">=",
"2.0.0"
]
]
}
],
"lcname": "qagen"
}