在企业环境中,准确高效地从大量非结构化数据(如 PDF 文件)中检索信息至关重要。基于检索增强生成(RAG)的系统在这方面发挥着重要作用,但提升其准确性是一个复杂且具有挑战性的任务。本文将详细介绍提高企业 RAG 准确性的逐步指南,涵盖从数据提取到检索的各个关键步骤。
1. 从 PDF 中提取知识
1.1 上传与记录创建
用户上传 PDF 文件(未来还将支持音频和视频等其他文件类型)。系统将文件保存到磁盘(近期计划迁移到 AWS S3 存储桶以更好地满足企业需求),并在数据库中插入记录,创建处理状态条目。使用支持多种数据类型、混合搜索和单次检索的 SingleStore 数据库。同时,将处理 PDF 的任务放入后台队列,通过 Redis 和 Celery 进行异步处理和跟踪。
# Pseudo-code
save_file_to_disk(pdf)
db_insert(document_record, status=”started”)
queue_processing_task(pdf)
1.2 解析与分块 PDF
打开文件并验证大小限制和密码保护,若文件不可读则尽早终止处理。将文件内容提取为文本或 Markdown 格式,可使用 Llamaparse(来自 Llamaindex)替代之前的 PyMudf,其免费版每天支持 1000 次文档解析,并能更好地处理表格和图像提取。分析文档结构(如目录、标题等),利用 Gemini Flash 2.0 基于语义将文本分割成有意义的块,若语义分块失败,则采用简单的分割方式,并在块之间添加重叠部分以保持上下文连贯性。
# Pseudo-code
validate_pdf(pdf)
text = extract_text(pdf)
chunks = semantic_chunking(text) or fallback_chunking(text)
add_overlaps(chunks)
1.3 生成嵌入
使用嵌入模型将每个文本块转换为高维向量,例如使用 OpenAI 的 large ada 模型,维度设置为 1536。将文本块及其嵌入向量存储在数据库中,在 SingleStore 中,将文本块和文本分别存储在同一表的不同列,便于维护和检索。
# Pseudo-code
for chunk in chunks:
vector = generate_embedding(chunk.text)
db_insert(embedding_record, vector)
1.4 使用大语言模型提取实体和关系
这一步对整体准确性影响很大。将语义组织好的文本块发送给 OpenAI,通过特定的提示要求其返回每个块中的实体和关系,