RAG:如何从0到1搭建一个RAG应用

RAG——从0到1快速搭建RAG应用 本文介绍了基于LangChain框架构建RAG(检索增强生成)应用的技术方案,涵盖核心模块选型与实现流程。技术栈包括:LangChain应用框架、pypdf文档解析、RecursiveCharacterTextSplitter文本分块、bge-small-zh-v1.5向量模型、Faiss向量库和通义千问大模型。文章详细说明了开发环境配置步骤,包括虚拟环境创建、依赖库安装和模型下载。核心代码分为索引、检索、生成三大流程,索引流程完成PDF文档解析、分块和向量化存储;检索流程实现查询向量化和相似度匹配;生成流 阅读详情

通过本文你可以了解到:

  • 什么是RAG?
  • 如何搭建一个RAG应用?
  • 目前开源的RAG应用有哪些?

大模型学习参考: 1.大模型学习资料整理:大模型学习资料整理:如何从0到1学习大模型,搭建个人或企业RAG系统,如何评估与优化(更新中…)2.streamlit入门和简单使用:streamlit:如何快速构建一个应用,不会前端也能写出好看的界面

RAG简介

img

检索增强生成(Retrieval Augmented Generation,RAG)是一种强大的工具,整合了从庞大知识库中检索到的相关信息,并以此为基础,指导大型语言模型生成更为精准的答案,从而显著提升了回答的准确性与深度。

2020 年,Meta AI 研究人员提出了RAG的方法,用于提高 LLM 在特定任务上的性能。LLM 擅长语言理解、推理和生成等任务,但也存在一些问题:

  • 信息滞后:LLM 的知识是静态的,来源于当时训练时的数据,也就是 LLM 无法直接提供最新的信息。
  • 模型幻觉:实践表明,当前的生成式 AI 技术存在一定的幻觉,而在一些常见的业务应用中,我们是希望保证事实性的。
  • 私有数据匮乏:LLM 的训练数据主要来源于互联网公开的数据,而垂类领域、企业内部等有很多专属知识,这部分是 LLM 无法直接提供的。
  • 内容不可追溯: LLM 生成的内容往往缺乏明确的信息来源,影响内容的可信度。RAG 将生成内容与检索到的原始资料建立链接,增强了内容的可追溯性,从而提升了用户对生成内容的信任度。
  • 长文本处理能力较弱: LLM 在理解和生成长篇内容时受限于有限的上下文窗口,且必须按顺序处理内容,输入越长,速度越慢。RAG 通过检索和整合长文本信息,强化了模型对长上下文的理解和生成,有效突破了输入长度的限制,同时降低了调用成本,并提升了整体的处理效率。

RAG 通过将检索到的相关信息提供给 LLM,让 LLM 进行参考生成,可以较好地缓解上述问题。因此,合理使用 RAG 可以拓展 LLM 的知识边界,使其不仅能够访问专属知识库,还能动态地引入最新的数据,从而在生成响应时提供更准确、更新的信息。

RAG组成部分

自定义知识库,用于RAG检索的知识来源:

  • 结构化的数据库形态:比如MySQL
  • 非结构化的文档体系:比如文件、图片、音频、视频

RAG 是一个完整的系统,其工作流程可以简单地分为数据处理、检索、增强和生成四个阶段:

数据处理阶段

对原始数据进行清洗和处理。 将处理后的数据转化为检索模型可以使用的格式。 将处理后的数据存储在对应的数据库中。

检索阶段

将用户的问题输入到检索系统中,从数据库中检索相关信息。

增强阶段

对检索到的信息进行处理和增强,以便生成模型可以更好地理解和使用。

生成阶段

将增强后的信息输入到生成模型中,生成模型根据这些信息生成答案。

搭建RAG应用

数据处理

数据清洗和处理

数据处理阶段,一般需要对知识库中的数据进行数据清洗,比如去掉多余的换行、特殊符号,然后加载处理后的文件和分块:

  • 加载文件:使用langchain下的document_loaders加载pdf、docs、txt、md等格式文件
  • 文本分块:分块的方式有很多,选择不同的分块方法、分块大小、chunk_overlap,对最后的检索结果有影响,这一阶段也有RAG的优化点之一
import os

from langchain_community.document_loaders import PyPDFLoader, Docx2txtLoader, UnstructuredFileLoader
from langchain_text_splitters import RecursiveCharacterTextSplitter


def load_document(file):
    """
    加载PDF、DOC、TXT文档
    :param file:
    :return:
    """
    name, extension = os.path.splitext(file)

    if extension == '.pdf':
        print(f'Loading {file}')
        loader = PyPDFLoader(file)
    elif extension == '.docx':
        print(f'Loading {file}')
        loader = Docx2txtLoader(file)
    elif extension == '.txt':
        loader = UnstructuredFileLoader(file)
    else:
        print('Document format is not supported!')
        return None
    data = loader.load()
    return data


def chunk_data(data, chunk_size=256, chunk_overlap=150):
    """
    将数据分割成块
    :param data:
    :param chunk_size: chunk块大小
    :param chunk_overlap: 重叠部分大小
    :return:
    """
    text_splitter = RecursiveCharacterTextSplitter(chunk_size=chunk_size, chunk_overlap=chunk_overlap)
    chunks = text_splitter.split_documents(data)
    return chunks

embedding模型存储

将分块后的文本,使用embedding模型持久化存储,目前常用的中文模型是bge-large-zh-v1.5。持久化存储后,避免每次都去embedding一次,消耗很长的时间。下次使用时,直接加载模型就可以了。

import os

from langchain_community.embeddings import HuggingFaceBgeEmbeddings, OpenAIEmbeddings
from langchain_community.vectorstores import Chroma, FAISS


def get_embedding(embedding_name):
    """
    根据embedding名称去加载embedding模型
    :param embedding_name: 路径或者名称
    :return:
    """
    if embedding_name == "bge":
        embedding_path = os.environ[embedding_name]
        model_kwargs = {'device': 'cpu'}
        return HuggingFaceBgeEmbeddings(model_name=embedding_path, model_kwargs=model_kwargs)
    if embedding_name == "bce":
        return None


# create embeddings using OpenAIEmbeddings() and save them in a Chroma vector store
def create_embeddings_chroma(chunks):
    embeddings = OpenAIEmbeddings()
    vector_store = Chroma.from_documents(chunks, embeddings)

    # if you want to use a specific directory for chromadb
    # vector_store = Chroma.from_documents(chunks, embeddings, persist_directory='./mychroma_db')
    return vector_store


def create_embeddings_faiss(vector_db_path, embedding_name, chunks):
    """
    使用FAISS向量数据库,并保存
    :param vector_db_path: 向量
    :param embedding_name:
    :param chunks:
    :return:
    """
    embeddings = get_embedding(embedding_name)
    db = FAISS.from_documents(chunks, embeddings)

    if not os.path.isdir(vector_db_path):
        os.mkdir(vector_db_path)

    db.save_local(folder_path=vector_db_path)
    return db


def load_embeddings_faiss(vector_db_path, embedding_name):
    """
    加载向量库
    :param vector_db_path:
    :param embedding_name:
    :return:
    """
    embeddings = get_embedding(embedding_name)
    db = FAISS.load_local(vector_db_path, embeddings, allow_dangerous_deserialization=True)
    return db

构建模型

采用了函数和类两种方式定义模型:

  • 函数:get_llm_model定义了基本的参数,model、prompt、temperature、max_tokens、n_ctx
  • 自定义类:
import os
import sys
import time
from abc import ABC

from langchain_core.callbacks import CallbackManagerForLLMRun
from llama_cpp import Llama
from langchain.llms.base import LLM
from pydantic import Field
from typing import Dict, Any, Mapping, Optional, List

BASE_DIR = os.path.dirname(__file__)
# PRJ_DIR上层目录
# PRJ_DIR = os.path.abspath(os.path.join(BASE_DIR, ".."))
sys.path.append(BASE_DIR)

def get_llm_model(
        prompt: str = None,
        model: str = None,
        temperature: float = 0.0,
        max_token: int = 2048,
        n_ctx: int = 512):
    """
    根据模型名称去加载模型,返回response数据
    :param prompt:
    :param model:
    :param temperature:
    :param max_token:
    :param n_ctx:
    :return:
    """
    if model in ['Qwen_q2']:
        model_path = os.environ[model]
        llm = Llama(model_path=model_path, n_ctx=n_ctx)
        start = time.time()
        response = llm.create_chat_completion(
            messages=[
                {
                    "role": "system",
                    "content": "你是一个智能超级助手,请用专业的词语回答问题,整体上下文带有逻辑性,如果不知道,请不要乱说",
                },
                {
                    "role": "user",
                    "content": "{}".format(prompt)
                },
            ],
            temperature=temperature,
            max_tokens=max_token,
            stream=False
        )
        cost = time.time() - start
        print(f"模型生成时间:{cost}")
        print(f"大模型回复:\n{response}")
        return response['choices'][0]['message']['content']

class QwenLLM(LLM):
    """
    自定义QwenLLM
    """
    model_name: str = "Qwen_q2"
    # 访问时延上限
    request_timeout: float = None
    # 温度系数
    temperature: float = 0.1
    # 窗口大小
    n_ctx = 2048
    # token大小
    max_tokens = 1024
    # 必备的可选参数
    model_kwargs: Dict[str, Any] = Field(default_factory=dict)

    def _call(self, prompt: str, stop: Optional[List[str]] = None,
              run_manager: Optional[CallbackManagerForLLMRun] = None,
              **kwargs: Any):
        qwen_path = os.environ[self.model_name]
        print("qwen_path:", qwen_path)

        llm = Llama(model_path=qwen_path, n_ctx=self.n_ctx)

        response = llm.create_chat_completion(
            messages=[
                {
                    "role": "system",
                    "content": "你是一个智能超级助手,请用[中文]专业的词语回答问题,整体上下文带有逻辑性,并以markdown格式输出",
                },
                {
                    "role": "user",
                    "content": "{}".format(prompt)
                },
            ],
            temperature=self.temperature,
            max_tokens=self.max_tokens,
            stream=False
        )

        # prompt工程提示

        # print(f"Qwen prompt: \n{prompt}")
        # response = lla(
        #     prompt=prompt,
        #     temperature=self.temperature,
        #     max_tokens=self.max_tokens
        # )
        print(f"Qwen response: \n{response}")
        # return response['choices'][0]['text']
        return response['choices'][0]['message']['content']

    @property
    def _llm_type(self) -> str:
        return "Llama3"

        # 定义一个返回默认参数的方法

    @property
    def _default_params(self) -> Dict[str, Any]:
        """获取调用默认参数。"""
        normal_params = {
            "temperature": self.temperature,
            "request_timeout": self.request_timeout,
            "n_ctx": self.n_ctx,
            "max_tokens": self.max_tokens
        }
        # print(type(self.model_kwargs))
        return {**normal_params}

    @property
    def _identifying_params(self) -> Mapping[str, Any]:
        """Get the identifying parameters."""
        return {**{"model_name": self.model_name}, **self._default_params}

构建应用

import sys

import streamlit as st
import os
from langchain.chains import RetrievalQA
from langchain.chat_models import ChatOpenAI
import tiktoken
from dotenv import load_dotenv, find_dotenv
from langchain_core.prompts import PromptTemplate

BASE_DIR = os.path.dirname(__file__)
PRJ_DIR = os.path.abspath(os.path.join(BASE_DIR, ".."))
sys.path.append(PRJ_DIR)

from streamlit_demo.custom_llm import QwenLLM
from streamlit_demo.embedding_oper import create_embeddings_faiss, create_embeddings_chroma, load_embeddings_faiss
from streamlit_demo.prepare_data import load_document, chunk_data

_ = load_dotenv(find_dotenv(), override=True)
vector_db_path = os.path.join(BASE_DIR, "vector_db")
print(f"vector_db_path: {vector_db_path}")

DEFAULT_TEMPLATE = """
    你是一个聪明的超级智能助手,请用专业且富有逻辑顺序的句子回复,并以中文形式且markdown形式输出。
    检索到的信息:
    {context}
    问题:
    {question}
"""


def ask_and_get_answer_from_local(model_name, vector_db, prompt, top_k=5):
    """
    从本地加载大模型
    :param model_name: 模型名称
    :param vector_db:
    :param prompt:
    :param top_k:
    :return:
    """
    docs_and_scores = vector_db.similarity_search_with_score(prompt, k=top_k)
    print("docs_and_scores: ", docs_and_scores)
    # knowledge = [doc.page_content for doc in docs_and_scores]
    # print("检索到的知识:", knowledge)
    if model_name == "Qwen_q2":
        llm = QwenLLM(model_name=model_name, temperature=0.4)
    prompt_template = PromptTemplate(input_variables=["context", "question"], template=DEFAULT_TEMPLATE)
    retriever = vector_db.as_retriever(search_type='similarity', search_kwargs={'k': top_k})
    chain = RetrievalQA.from_chain_type(llm=llm,
                                        chain_type="stuff",
                                        retriever=retriever,
                                        chain_type_kwargs={"prompt": prompt_template},
                                        return_source_documents=True)
    answer = chain({"query": prompt, "top_k": top_k})
    print(f"answers: {answer}")
    # answer = chain.run(prompt)
    # answer = answer['choices'][0]['message']['content']
    answer = answer['result']
    return answer


def ask_and_get_answer(vector_store, q, k=3):
    llm = ChatOpenAI(model='gpt-3.5-turbo', temperature=1)
    retriever = vector_store.as_retriever(search_type='similarity', search_kwargs={'k': k})
    chain = RetrievalQA.from_chain_type(llm=llm, chain_type="stuff", retriever=retriever)

    answer = chain.run(q)
    return answer


# calculate embedding cost using tiktoken
def calculate_embedding_cost(texts):
    enc = tiktoken.encoding_for_model('text-embedding-ada-002')
    total_tokens = sum([len(enc.encode(page.page_content)) for page in texts])
    # print(f'Total Tokens: {total_tokens}')
    # print(f'Embedding Cost in USD: {total_tokens / 1000 * 0.0004:.6f}')
    return total_tokens, total_tokens / 1000 * 0.0004


# clear the chat history from streamlit session state
def clear_history():
    if 'history' in st.session_state:
        del st.session_state['history']


if __name__ == "__main__":

    # st.image('img.png')
    st.subheader('LLM Question-Answering Application 🤖')
    with st.sidebar:
        # text_input for the OpenAI API key (alternative to python-dotenv and .env)
        api_key = st.text_input('OpenAI API Key:', type='password')
        if api_key:
            os.environ['OPENAI_API_KEY'] = api_key
        llm = st.selectbox(
            label="请选择本地大模型",
            options=('Qwen_q2', 'Qwen_q6')
        )
        # 向量数据库
        embedding = st.selectbox(
            "请选择向量数据库",
            ('FAISS', 'Chroma')
        )

        # file uploader widget
        uploaded_file = st.file_uploader('上传文件:', type=['pdf', 'docx', 'txt'])

        # chunk size number widget
        chunk_size = st.number_input('chunk_size:', min_value=100, max_value=2048, value=512, on_change=clear_history)

        # chunk overlap
        chunk_overlap = st.number_input(label="chunk_overlap", min_value=0, max_value=1024, value=150,
                                        on_change=clear_history)

        # k number input widget
        k = st.number_input('top_k', min_value=1, max_value=20, value=3, on_change=clear_history)

        # add data button widget
        add_data = st.button('添加数据', on_click=clear_history)

        # 输出方式
        output_type = st.selectbox("选择输出方式", ('普通输出', '流式输出'))

        if uploaded_file and add_data:  # if the user browsed a file
            with st.spinner('Reading, chunking and embedding file ...'):
                # writing the file from RAM to the current directory on disk
                bytes_data = uploaded_file.read()
                file_name = os.path.join('./', uploaded_file.name)
                with open(file_name, 'wb') as f:
                    f.write(bytes_data)

                data = load_document(file_name)
                chunks = chunk_data(data, chunk_size=chunk_size, chunk_overlap=chunk_overlap)
                st.write(f'Chunk size: {chunk_size}, chunk_overlap: {len(chunks)} Chunks: {len(chunks)}')

                tokens, embedding_cost = calculate_embedding_cost(chunks)
                st.write(f'Embedding cost: ${embedding_cost:.4f}')

                # creating the embeddings and returning the Chroma vector store
                # 指定选择向量库和embedding类型,还可改进
                if embedding == "FAISS":
                    vector_store = create_embeddings_faiss(vector_db_path=vector_db_path, embedding_name="bge",
                                                           chunks=chunks)
                elif embedding == "Chroma":
                    vector_store = create_embeddings_chroma(chunks)

                # saving the vector store in the streamlit session state (to be persistent between reruns)
                st.session_state.vs = vector_store
                st.success('File uploaded, chunked and embedded successfully.')

    # 初始化history
    if "messages" not in st.session_state:
        st.session_state.messages = []

    # 展示对话
    for msg in st.session_state.messages:
        with st.chat_message(msg['role']):
            st.markdown(msg["content"])

    # React to user input
    if prompt := st.chat_input("Say something"):
        # Display user message in chat message container
        with st.chat_message("user"):
            st.markdown(prompt)
        # Add user message to chat history
        st.session_state.messages.append({"role": "user", "content": prompt})

    # load local vector db
    if 'vs' not in st.session_state:
        # st.warning(body='正在努力加载模型中...', icon="⚠️")
        vector_store = load_embeddings_faiss(vector_db_path, "bge")
        st.session_state.vs = vector_store
        st.toast('Load vector store db success!', icon='😍')

    # 普通方式输出
    if prompt is not None:
        vector_store = st.session_state.vs
        # if vector_store is None:
        #     st.warning(body='正在努力加载模型中,稍后再试', icon="⚠️")
        if output_type == "普通输出" and vector_store is not None:
            response = ""
            if llm == "GPT":
                response = ask_and_get_answer(vector_store, prompt, k)
            elif llm == "Qwen_q2":
                response = ask_and_get_answer_from_local(model_name="Qwen_q2", vector_db=vector_store, prompt=prompt, top_k=k)
            # Display assistant response in chat message container
            with st.chat_message("assistant"):
                st.markdown(response)
            # Add assistant response to chat history
            st.session_state.messages.append({"role": "assistant", "content": response})
        else:
            # 流式输出
            # stream_res = get_llm_model_with_stream(prompt=prompt, model="Qwen_q2")
            # with st.chat_message("assistant"):
            #     content = st.write_stream(stream_res)
            # print("流式输出:", content)
            # st.session_state.messages.append({"role": "assistant", "content": content})
            print("流式输出")


# run the app: streamlit run ./chat_doc.py

结果展示

使用步骤:

  1. 选择参数,然后上传本地的文件
  2. 开始添加数据,用于数据处理和embedding持久化存储

img

img

开源的RAG应用

QAnything: https://github.com/netease-youdao/QAnything

AnythingLLM:https://github.com/Mintplex-Labs/anything-llm

ragflow:https://github.com/infiniflow/ragflow/blob/main/README_zh.md

如何学习AI大模型?

大模型时代,火爆出圈的LLM大模型让程序员们开始重新评估自己的本领。 “AI会取代那些行业?”“谁的饭碗又将不保了?”等问题热议不断。

不如成为「掌握AI工具的技术人」,毕竟AI时代,谁先尝试,谁就能占得先机!

想正式转到一些新兴的 AI 行业,不仅需要系统的学习AI大模型。同时也要跟已有的技能结合,辅助编程提效,或上手实操应用,增加自己的职场竞争力。

但是LLM相关的内容很多,现在网上的老课程老教材关于LLM又太少。所以现在小白入门就只能靠自学,学习成本和门槛很高

那么我作为一名热心肠的互联网老兵,我意识到有很多经验和知识值得分享给大家,希望可以帮助到更多学习大模型的人!至于能学习到多少就看你的学习毅力和能力了 。我已将重要的AI大模型资料包括AI大模型入门学习思维导图、精品AI大模型学习书籍手册、视频教程、实战学习等录播视频免费分享出来。

这份完整版的大模型 AI 学习资料已经上传优快云,朋友们如果需要可以微信扫描下方优快云官方认证二维码免费领取【保证100%免费】

👉 福利来袭优快云大礼包:《2025最全AI大模型学习资源包》免费分享,安全可点 👈

全套AGI大模型学习大纲+路线

AI大模型时代的学习之旅:从基础到前沿,掌握人工智能的核心技能!

img

640套AI大模型报告合集

这套包含640份报告的合集,涵盖了AI大模型的理论研究、技术实现、行业应用等多个方面。无论您是科研人员、工程师,还是对AI大模型感兴趣的爱好者,这套报告合集都将为您提供宝贵的信息和启示。

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

👉学会后的收获:👈
• 基于大模型全栈工程实现(前端、后端、产品经理、设计、数据分析等),通过这门课可获得不同能力;

• 能够利用大模型解决相关实际项目需求: 大数据时代,越来越多的企业和机构需要处理海量数据,利用大模型技术可以更好地处理这些数据,提高数据分析和决策的准确性。因此,掌握大模型应用开发技能,可以让程序员更好地应对实际项目需求;

• 基于大模型和企业数据AI应用开发,实现大模型理论、掌握GPU算力、硬件、LangChain开发框架和项目实战技能, 学会Fine-tuning垂直训练大模型(数据准备、数据蒸馏、大模型部署)一站式掌握;

• 能够完成时下热门大模型垂直领域模型训练能力,提高程序员的编码能力: 大模型应用开发需要掌握机器学习算法、深度学习框架等技术,这些技术的掌握可以提高程序员的编码能力和分析能力,让程序员更加熟练地编写高质量的代码。

👉 福利来袭优快云大礼包:《2025最全AI大模型学习资源包》免费分享,安全可点 👈

img

这份完整版的大模型 AI 学习资料已经上传优快云,朋友们如果需要可以微信扫描下方优快云官方认证二维码免费领取【保证100%免费】

作为普通人,入局大模型时代需要持续学习和实践,不断提高自己的技能和认知水平,同时也需要有责任感和伦理意识,为人工智能的健康发展贡献力量。

RAG实战1-基于LlamaIndex构建第一个RAG应用 llama-index-embeddings-huggingface允许我们使用本地的embedding模型去完成文档的切分和编码等操作;llama-index-llms-huggingface允许我们使用本地的大模型去开发RAG应用。4,下载模型文件:git clone https://www.modelscope.cn/qwen/Qwen1.5-14B-Chat.git。中广泛应用的技术,旨在将高维度的数据(如文字、图片、视频等)映射到低维度的空间。3,下载embedding模型权重:‌。 阅读详情

相关推荐

使用autodl服务器运行CasMVSNet以及使用colmap产生的数据

MVSNet学习

qq_44708206的博客 3274

LLM - Dify(1.0.1)搭建本地私有RAG知识库完整指南

由于 Dify 内置了构建 LLM 应用所需的关键技术栈,包括对数百个模型的支持、直观的 Prompt 编排界面、高质量的 RAG 引擎、稳健的 Agent 框架、灵活的流程编排,并同时提供了一套易用的界面和 API。它融合了后端即服务(Backend as Service)和 LLMOps 的理念,使开发者可以快速搭建生产级的生成式 AI 应用。需要根据测试结果,发现回答不准确或性能不佳,可以对数据进行进一步的清洗和整理,优化索引结构,调整 RAG 模型的参数等。在 Dify 的界面中,点击用户名。

小工匠 5963

ABB机器人ModbusTCP通信实战:如何高效传输Float数据到PLC(附完整代码)

本文详细介绍了ABB机器人通过ModbusTCP协议高效传输Float数据到PLC的实战方法,包括底层逻辑解析、RAPID程序架构设计、PLC服务器配置及现场调试技巧。特别针对浮点数据传输中的字节顺序问题提供了解决方案,并附有完整代码示例,助力工程师快速实现工业自动化设备间的高精度数据交互。

weixin_30836759的博客 482

一文读懂RAGFlow:从 0 到 1教你搭建RAG知识库

RAGFlow是一种融合了数据检索与生成式模型的新型系统架构,其核心思想在于将大规模检索系统与先进的生成式模型(如Transformer、GPT系列)相结合,从而在回答查询时既能利用海量数据的知识库,又能生成符合上下文语义的自然语言回复。该系统主要包含两个关键模块:数据检索模块和生成模块。数据检索模块负责在海量数据中快速定位相关信息,而生成模块则基于检索结果生成高质量的回答或文本内容。

2301_76168381的博客 3万+

NDIAurora 6D、5D传感器裸线焊接与烧录 6D传感器型号:10001742;5D传感器型号:610157

NDI Aurora 6D、5D传感器裸线焊接与烧录

yanghong2000719的博客 1201

【项目实战】Qt6 录制屏幕、录制声音生成MP4、AVI、MA3等(完整源码,可直接编译使用)

本文将详细介绍如何利用Qt6多媒体模块中的QMediaCaptureSession、QMediaRecorder、QScreenCapture、QAudioInput、QMediaFormat等功能,实现对屏幕和声音的录制,并生成常见的媒体格式文件,如MP4、AVI、MA3等。我们将探讨如何利用这些功能来实现灵活的视频和音频参数设置,以满足不同需求下的录制和生成要求。我们将重点讨论如何配置视频和音频参数,包括分辨率、帧率、编解码器选择、音频采样率、声道设置等。

yegu001的博客 4939

使用 langchain4j 快速搭建一个 RAG 应用。

•。

2401_85280106的博客 1963

【TCAD】AlGaN 器件的Sentaurus仿真

否则,必须在 LatticeParameters Sentaurus Device 的参数文件中的部分。Sentaurus Device 有两个工具实例:第一个工具实例, sd_fdiv ,模拟正向偏置特性,第二个工具实例, sd_rviv ,模拟反向偏置特性直至击穿。对于牛顿求解器,通常应该将非线性迭代次数限制为一个足够小的值,例如 Iterations=20 ,同时通过指定非阻尼迭代次数高于允许的牛顿迭代次数来避免解的阻尼( NotDamped=30 )。晶胞中的 Ga-N 键为橙色。

荷塘阅色 1213

使用 Milvus、vLLM 和 Llama 3.1 搭建 RAG 应用

Milvus 是一款开源的分布式向量数据库,可用于存储、索引和搜索向量数据,适用于生成式 AI(GenAI)应用。Milvus 支持 hybrid search、元数据过滤、重排(Reranking),能够高效处理万亿规模的向量,助力开发者搭建 AI 和 ML 应用。您可以在本地运行 Milvus standalone 或 cluster 版本,或者使用全托管的 Milvus 服务——Zilliz Cloud。

m0_59235245的博客 1921

2025美赛C题奥运奖牌榜模型(附代码+全保姆教程)Models for Olympic Medal Tables

伟大教练”效应的测量方法定义奖牌变化率:−−​如果变化率显著为正,且超出历史平均增长率,则认为存在“伟大教练”效应。使用统计方法(如t检验)验证教练到来是否带来显著性差异。

博客 6371

5、模糊风险评估

本文介绍了基于模糊逻辑的风险评估方法,探讨了如何在不确定、不完整信息环境下进行高效的风险分析。文章涵盖了模糊集合与隶属度函数的基本概念、模糊推理系统的流程,并结合犯罪风险、金融风险和医疗诊断等实际案例,展示了模糊风险评估的应用价值和技术细节。此外,还介绍了模糊贝叶斯网络、模糊综合评价等进阶工具与方法,为多领域风险管理提供了理论支持和实践指导。

mango的博客 179

检索增强生成(RAG)实战1-基于LlamaIndex构建第一个RAG应用

本文将介绍如何使用LlamaIndex构建一个非常简单的RAG应用。通过该案例,可以初步了解LlamaIndex构建RAG应用的大体流程。

pythonhy的博客 2318

提示词工程在机器翻译质量提升中的应用

Introduction to Prompt Engineering in Machine Translation Quality Improvement Keywords

AI天才研究院 1151

从0到1搭建一个Rag引擎(ollama+Qwen3)

大型语言模型(LLM)在生成语言时,可能会产生幻觉或不准确的结果。这些问题包括为了解决这些问题,检索增强生成(Retrieval-Augmented Generation, RAG)应运而生。RAG,极大地提升了模型输出的准确性和相关性。RAG 不仅提高了知识更新的效率,还显著增强了生成内容的可追溯性,使其在实际应用中更具实用性和可信度。RAG技术诞生的原因:大模型最大对话上下文限制。

qq_58158950的博客 1025

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

如何使用 Ollama和DeepSeek R1搭建RAG系统?

RAG(Retrieval-Augmented Generation,检索增强生成) 是一种结合了信息检索技术与语言生成模型的人工智能技术。该技术通过从外部知识库中检索相关信息,并将其作为提示(Prompt)输入给大型语言模型(LLMs),以增强模型处理知识密集型任务的能力,如问答、文本摘要、内容生成等。RAG的目的是通过从外部知识库检索相关信息来辅助大语言模型生成更准确、更丰富的文本内容。那我们如何理解RAG的检索、增强和生成呢?检索:检索是RAG流程的第一步,从预先建立的知识库中检索与问题相关的信息。

2401_84495872的博客 829

锂电池充电器电路设计 里面有电路

锂电池充电器电路设计 里面有电路 3.7V升压到5V电路设计。

如何速成RAG+Agent框架大模型应用搭建

二、大模型发展现状目前大模型发展笼统的可以分为两个部分,自然语言处理大模型(Qwen语言系列等)和多模态大模型,同时多模态大模型又分为多模态理解(Qwen-VL、Qwen-Audio等)和多模态生成(万相、EMO等)。自然语言处理在自然语言处理领域,短短的2个月内,大家已经看到了价格的急剧下降,这是得益诸如OpenAI的ChatGPT系列、Llama、通义、GLM等标志性大模型的发布和应用,也代表着这个技术在算法和模型层面上的进入了成熟的新阶段。

python1234_的博客 1374

IEM模型,地表粗糙度模拟

利用微波反演土壤水分时候,利用IEM模型可以实现对随机地表的模拟

AI大模型:从 RAG 1.0到RAG 2.0,这次做对了什么?

RAG是目前最流行的补充生成式人工智能模型的方式,最近 RAG 的开创者提出了新的上下文语言模型 (CLM) ,他们称之为“ RAG 2.0 ”。

pythonhy的博客 1011

LangChain1.0教程:使用RAG Agent和RAG Chain构建RAG智能体

本教程将通过 RAG Agent 和 RAG Chain 展示如何基于非结构化文本数据源构建一个简单的问答应用。

python1234567_的博客 837

从 RAG 1.0到RAG 2.0,这次做对了什么?

RAG是目前最流行的补充生成式人工智能模型的方式,最近 RAG 的开创者提出了新的上下文语言模型 (CLM) ,他们称之为“ RAG 2.0 ”。

2301_81940605的博客 1655
上一篇: 我用DeepSeek做内容,1天生产30篇小红书笔记
下一篇: 0工作经验,面试了12家AI大模型公司,拿到了3个offer
我爱学大模型
博客等级 码龄3年 7883粉丝 687原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值