赞
踩
随着大型语言模型(LLMs)的兴起,我们见证了一种新的工具类别的诞生。然而,LLMs 也存在局限性,尤其是当面对需要最新信息或专有数据的商业用例时。本文将介绍如何通过微调和 RAG 来解决这些问题。
传统 LLMs 训练成本高昂,且只能访问公共信息。对于商业用途,需要模型能够提供基于内部知识的最新回应。文章介绍了两种解决这一问题的方法:微调和 RAG。
微调是针对特定数据集进一步训练预训练模型的过程,使其适应特定任务或领域。这类似于给一个通才型助手提供额外的、针对性的训练,使其成为某个特定领域的专家。
RAG 是一种模型从外部来源检索相关信息以生成更准确、更有信息量回应的方法。与传统依赖预训练知识的模型不同,RAG 通过数据库或搜索引擎查找额外数据,并结合这些数据生成回应。
面对 LLMs 的法律和安全问题,开源社区提供了解决方案。自 Meta 发布了首个 Llama 模型以来,开源社区迅速响应,为本地实验提供了机会。
文章通过图解介绍了 RAG 的核心工作流程,包括文本分块、向量化存储、语义搜索和组合提示。
文本分块:将内容分割成文本块,以便更好地检索相关内容。
向量化存储:将文本转换为向量并存储在向量数据库中。
语义搜索:使用数值表示进行内容搜索,返回相关内容。
组合提示:将问题与相关内容结合,生成更准确的提示。
文章通过示例代码,展示了如何使用 Langchain、ChromaDB、Ollama 和 Streamlit 构建 RAG 应用程序。
Langchain 是一个构建大型语言模型(LLM)驱动应用程序的框架。它通过将链、代理和检索策略整合在一起,简化了从概念到实际应用的整个开发过程。Langchain 的核心是其链的概念,这些链构成了应用程序的认知架构。
ChromaDB 是一款开源的轻量级矢量数据库,非常适合小规模服务和用例。它在任何基于 LLM 的应用程序中都扮演着重要角色,因为它以矢量格式存储文本数据,这是 AI 和 ML 模型原生使用的数据格式,可以视为 AI 的内存。
Ollama 是一个工具,允许用户轻松在本地运行开源模型。它简化了将这些模型集成到应用程序中的复杂性,使得开发者可以快速利用最新的模型,如 Meta 的 Llama3,进行本地开发和测试。
Streamlit 是一个开源框架,用于快速且容易地在机器学习和数据科学应用程序之上构建 Web 界面。它允许开发者使用纯 Python 代码将数据脚本转换为可共享的 Web 应用程序,无需前端开发经验,非常适合快速原型开发和应用部署。
使用 Poetry 进行依赖管理,并安装了必要的依赖项。
poetry add langchain chromadb streamlit
使用 Streamlit 创建简单的界面,允许用户上传 PDF 文档。
def init_ui(): """init_ui Initializes the UI""" st.set_page_config(page_title="Langchain RAG Bot", layout="wide") st.title("Langchain RAG Bot") # Initialise session state if"chat_history"notin st.session_state: st.session_state.chat_history =[ AIMessage(content="Hello, I'm here to help. Ask me anything!") ] with st.sidebar: st.header("Document Capture") st.write("Please select a single document to use as context") st.markdown("**Please fill the below form :**") with st.form(key="Form", clear_on_submit=True): uploaded_file = st.file_uploader("Upload",type=["pdf"], key="pdf_upload") submit = st.form_submit_button(label="Upload") if submit: persist_file(uploaded_file)
确保本地运行 Ollama,以便创建正确格式的嵌入。
将文档内容转换为向量并存储在 ChromaDB 中。
def init_vector_store(): """ Initializes and returns ChromaDB vector store from document chunks Returns: ChromaDB: Initialized vector store """ # Get the first file - in reality this would be more robust files =[f for f in DATA_DIR.iterdir()if f.is_file] ifnot files: st.error("No files uploaded") returnNone # Get the path to the first file in the directory first_file = files[0].resolve() # Use the PDF loader in Langchain to fetch the document text loader =PyPDFLoader(first_file) document = loader.load_and_split() # Now we initialise the text splitter we will use on the document text_splitter =RecursiveCharacterTextSplitter() document_chunks = text_splitter.split_documents(document) # Lastly, we initialise the vector store using the split document vector_store =Chroma.from_documents( documents=document_chunks, embedding=OllamaEmbeddings(), persist_directory=str(DB_DIR), collection_name="pdf_v_db"# Important if you want to reference the DB later ) return vector_store
构建检索链,以便根据用户查询检索相关内容。
def get_related_context(vector_store: Chroma)->RetrieverOutputLike: """ Will retrieve the relevant context based on the user's query using Approximate Nearest Neighbor search (ANN) Args: vector_store (Chroma): The initialized vector store with context Returns: RetrieverOutputLike: The chain component to be used with the LLM """ # Specify the model to use llm =Ollama(model="llama3") # Here we are using the vector store as the source retriever = vector_store.as_retriever() # Create a prompt that will be used to query the vector store for related content prompt =ChatPromptTemplate.from_messages([ MessagesPlaceholder(variable_name="chat_history"), ("user","{input}"), ("user","Given the above conversation, generate a search query to look up to get information relevant to the conversation") ]) # Create the chain element which will fetch the relevant content from ChromaDB chain_element = create_history_aware_retriever(llm, retriever, prompt) return chain_element defget_context_aware_prompt(context_chain: RetrieverOutputLike)->Runnable: """ Combined the chain element to fetch content with one that then creates the prompt used to interact with the LLM Args: context_chain (RetrieverOutputLike): The retriever chain that can fetch related content from ChromaDB Returns: Runnable: The full runnable chain that can be executed """ # Specify the model to use llm =Ollama(model="llama3") # A standard prompt template which combined chat history with user query # NOTE: You MUST pass the context into the system message prompt =ChatPromptTemplate.from_messages([ ("system","You are a helpful assistant that can answer the users questions. Use provided context to answer the question as accurately as possible:\n\n{context}"), MessagesPlaceholder(variable_name="chat_history"), ("user","{input}") ]) # This method creates a chain for passing documents to a LLM docs_chain = create_stuff_documents_chain(llm, prompt) # Now we merge the context chain & docs chain to form the full prompt rag_chain = create_retrieval_chain(context_chain, docs_chain) return rag_chain
使用 Streamlit 的内置聊天界面与 RAG LLM 进行交互。
def get_response(user_query: str)->str: """ Will use the query to fetch context & form a query to send to an LLM. Responds with the result of the query Args: user_query (str): Query input but user Returns: str: Answer from the LLM """ context_chain = get_related_context(st.session_state.vector_store) rag_chain = get_context_aware_prompt(context_chain) res = rag_chain.invoke({ "chat_history": st.session_state.chat_history, "input": user_query }) return res["answer"] definit_chat_interface(): """ Initializes a chat interface which will leverage our rag chain & a local LLM to answer questions about the context provided """ user_query = st.chat_input("Ask a question....") if user_query isnotNoneand user_query !="": response = get_response(user_query) # Add the current chat to the chat history st.session_state.chat_history.append(HumanMessage(content=user_query)) st.session_state.chat_history.append(AIMessage(content=response)) # Print the chat history for message in st.session_state.chat_history: ifisinstance(message,HumanMessage): with st.chat_message("Human"): st.write(message.content) ifisinstance(message,AIMessage): with st.chat_message("AI"): st.write(message.content)
尽管 LLMs 功能强大,但它们并非没有缺点。通过一些创造性思维和正确的工具,可以将这些挑战转化为机遇。结合微调和 RAG,以及 Langchain、ChromaDB、Ollama 和 Streamlit 等开源模型和框架,可以为 LLMs 的实际应用提供强大的解决方案。
由于新岗位的生产效率,要优于被取代岗位的生产效率,所以实际上整个社会的生产效率是提升的。
但是具体到个人,只能说是:
“最先掌握AI的人,将会比较晚掌握AI的人有竞争优势”。
这句话,放在计算机、互联网、移动互联网的开局时期,都是一样的道理。
我在一线互联网企业工作十余年里,指导过不少同行后辈。帮助很多人得到了学习和成长。
我意识到有很多经验和知识值得分享给大家,也可以通过我们的能力和经验解答大家在人工智能学习中的很多困惑,所以在工作繁忙的情况下还是坚持各种整理和分享。但苦于知识传播途径有限,很多互联网行业朋友无法获得正确的资料得到学习提升,故此将并将重要的AI大模型资料包括AI大模型入门学习思维导图、精品AI大模型学习书籍手册、视频教程、实战学习等录播视频免费分享出来。
该阶段让大家对大模型 AI有一个最前沿的认识,对大模型 AI 的理解超过 95% 的人,可以在相关讨论时发表高级、不跟风、又接地气的见解,别人只会和 AI 聊天,而你能调教 AI,并能用代码将大模型和业务衔接。
该阶段我们正式进入大模型 AI 进阶实战学习,学会构造私有知识库,扩展 AI 的能力。快速开发一个完整的基于 agent 对话机器人。掌握功能最强的大模型开发框架,抓住最新的技术进展,适合 Python 和 JavaScript 程序员。
恭喜你,如果学到这里,你基本可以找到一份大模型 AI相关的工作,自己也能训练 GPT 了!通过微调,训练自己的垂直大模型,能独立训练开源多模态大模型,掌握更多技术方案。
到此为止,大概2个月的时间。你已经成为了一名“AI小子”。那么你还想往下探索吗?
对全球大模型从性能、吞吐量、成本等方面有一定的认知,可以在云端和本地等多种环境下部署大模型,找到适合自己的项目/创业方向,做一名被 AI 武装的产品经理。
学习是一个过程,只要学习就会有挑战。天道酬勤,你越努力,就会成为越优秀的自己。
如果你能在15天内完成所有的任务,那你堪称天才。然而,如果你能完成 60-70% 的内容,你就已经开始具备成为一名大模型 AI 的正确特征了。
保证100%免费
】Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。