为什么是LangChain?

文章目录

  • 一、前言
  • 二、认识langchain
    • 1. langchain的主要组成
    • 2. 总览LangChain
    • 2. LangChain的六大核心模块
      • 1. Models:模型统一接口
      • 2. `Prompts`:管理 LLM 输入
      • 3. `Chains`:将 LLM 与其他组件相结合,执行多个chain
      • 4. `Indexes`:访问外部数据
        • a. Loader 加载器
        • b. `Document` 文档(解决加载数据超过模型最大输入) 与 `Text Spltters` 文本分割
        • d. Vectorstores 向量数据库
        • e. Embedding
      • 5. `Memory`:记住以前的对话
      • 6. `Agents`:访问其他工具,自定义agent中所使用的工具
  • 三、经典示例
    • 1. 最简单的交互
    • 2. 构建本地知识库问答机器人
    • 3. 让输出内容 结构化起来
    • 4. 使用 Hugging Face 模型
    • 4. 通过自然语言执行SQL命令

一、前言

我们知道因为一些不得已的原因,一些国外比较优秀的技术,我们不能看到,比如,如果我们想要借助 OpenAI 或 Hugging Face 创建基于大语言模型的应用程序。若非一些特殊方法,是难以实现的。从cahtgpt发布到今天不过一年时间,市面上的LLM已经百花齐放,不得不感慨技术革命的速度,为了能轻松构建大语言模型应用。不得不提起一个非常强大的第三方开源库:LangChain 。
官方文档
这个库目前非常活跃,已经67Kstart了,每天都在迭代,更新速度飞快。

LangChain 是一个我们与大模型互动的一个桥梁。他主要拥有 2 个能力:

  1. 作为大模型与本地数据的一个器哦啊两联系起来,也就是将 LLM 模型与外部数据源进行连接
  2. 让开发者与 LLM 模型进行更加友好的交互

而且:LangChain 是一个旨在帮助您轻松构建大语言模型应用的框架,它可以帮助我们:

  1. 为各种不同基础模型提供统一接口(参见Models)
  2. 帮助管理提示的框架(参见Prompts),能够实现,多个prompt 配合使用。
  3. 一套中心化接口,用于处理长期记忆(Memory)、外部数据(Indexes)、其他 LLM(Chains)以及 LLM 无法处理的任务的其他代理(例如,计算或搜索)。
    LLM 模型:Large Language Model,大型语言模型

LangChain是一个用于开发由语言模型驱动的应用程序的框架。它使应用程序能够:
具有上下文意识:将语言模型与上下文源(提示指令,少量示例,基于其响应的内容等)联系起来。
推理:依靠语言模型进行推理(关于如何根据提供的上下文进行回答,采取什么行动等)。
朗链的主要价值支柱有:
组件:用于处理语言模型的抽象,以及每个抽象的实现集合。组件是模块化的,易于使用,无论你

二、认识langchain

1. langchain的主要组成

LangChain 6大核心模块

Models:从不同的 LLM 和嵌入模型中进行选择
Prompts:管理 LLM 输入
Chains:将 LLM 与其他组件相结合
Indexes:访问外部数据
Memory:记住以前的对话
Agents:访问其他工具

2. 总览LangChain

langchain是个优雅的框架。

Models:从不同的 LLM 和嵌入模型中进行选择
支持多种模型接口,比如 OpenAI、Hugging Face、AzureOpenAI …
Fake LLM,用于测试
缓存的支持,比如 in-mem(内存)、SQLite、Redis、SQL用量记录
支持流模式(就是一个字一个字的返回,类似打字效果)

Prompts:管理 LLM 输入
Prompt管理,支持各种自定义模板
拥有大量的文档加载器,比如 Email、Markdown、PDF、Youtube …

Indexes:访问外部数据
对索引的支持
文档分割器
向量化
对接向量存储与搜索,比如 Chroma、Pinecone、Qdrand

Chains:将 LLM 与其他组件相结合
LLMChain
各种工具Chain
LangChainHub

2. LangChain的六大核心模块

1. Models:模型统一接口

各种类型的模型和模型集成,比如OpenAI的各个API/GPT-4等等,为各种不同基础模型提供统一接口,也就是说在调用模型的时候,我们可以只通过 一个入口:
比如:这里以 ChatGPT为例,因为特殊原因,api的key,秘钥这些东西 需要申请。

import os
os.environ["OPENAI_API_KEY"] = '你的api key'
from langchain.llms import OpenAIllm = OpenAI(model_name="text-davinci-003",max_tokens=1024)
llm("啥是人工智能")
# 可以选择的模型。以及模型的最大输入 tokenmodel_token_mapping = {"gpt-4": 8192,"gpt-4-0314": 8192,"gpt-4-0613": 8192,"gpt-4-32k": 32768,"gpt-4-32k-0314": 32768,"gpt-4-32k-0613": 32768,"gpt-3.5-turbo": 4096,"gpt-3.5-turbo-0301": 4096,"gpt-3.5-turbo-0613": 4096,"gpt-3.5-turbo-16k": 16385,"gpt-3.5-turbo-16k-0613": 16385,"text-ada-001": 2049,"ada": 2049,"text-babbage-001": 2040,"babbage": 2049,"text-curie-001": 2049,"curie": 2049,"davinci": 2049,"text-davinci-003": 4097,"text-davinci-002": 4097,"code-davinci-002": 8001,"code-davinci-001": 8001,"code-cushman-002": 2048,"code-cushman-001": 2048,}

2. Prompts:管理 LLM 输入

from langchain import PromptTemplate, FewShotPromptTemplateexamples = [{"word": "高兴", "antonym": "悲伤"},{"word": "高大", "antonym": "矮小"},
]example_template = 
"""
词语: {word}
反义词: {antonym}\n
"""example_prompt = PromptTemplate(input_variables=["word", "antonym"],template=example_template,
)few_shot_prompt = FewShotPromptTemplate(examples=examples,example_prompt=example_prompt,prefix="给出输入词语的反义词",suffix="词语: {input}\n反义词:",input_variables=["input"],example_separator="\n",
)few_shot_prompt.format(input="美丽")
#上面的代码将生成一个提示模板,并根据提供的示例和输入组成以下提示:#给出输入词语的反义词#词语: 高兴
#反义词: 悲伤#词语: 高大
#反义词: 矮小#词语: 美丽
#反义词:

3. Chains:将 LLM 与其他组件相结合,执行多个chain

from langchain.llms import OpenAI
from langchain.chains import LLMChain
from langchain.prompts import PromptTemplate
from langchain.chains import SimpleSequentialChain# location 链
llm = OpenAI(temperature=1)
template = """Your job is to come up with a classic dish from the area that the users suggests.
% USER LOCATION
{user_location}YOUR RESPONSE:
"""
prompt_template = PromptTemplate(input_variables=["user_location"], template=template)
location_chain = LLMChain(llm=llm, prompt=prompt_template)# meal 链
template = """Given a meal, give a short and simple recipe on how to make that dish at home.
% MEAL
{user_meal}YOUR RESPONSE:
"""
prompt_template = PromptTemplate(input_variables=["user_meal"], template=template)
meal_chain = LLMChain(llm=llm, prompt=prompt_template)# 通过 SimpleSequentialChain 串联起来,第一个答案会被替换第二个中的user_meal,然后再进行询问
overall_chain = SimpleSequentialChain(chains=[location_chain, meal_chain], verbose=True)
review = overall_chain.run("Rome")

4. Indexes:访问外部数据

访问外部数据,不得不介绍几个额外的,功能,就是langchain自带的几个模块。配合这几个小模块实现,外部数据的访问

a. Loader 加载器

这个就是从指定源进行加载数据的。比如:文件夹 DirectoryLoader、Azure 存储 AzureBlobStorageContainerLoader、CSV文件 CSVLoader、印象笔记 EverNoteLoader、Google网盘 GoogleDriveLoader、任意的网页 UnstructuredHTMLLoader、PDF PyPDFLoader、S3 S3DirectoryLoader/S3FileLoader、Youtube YoutubeLoader 等等,上面只是简单的进行列举了几个,官方提供了超级的多的加载器供你使用。
关于这里的官方介绍

#示例:
from langchain.document_loaders import UnstructuredFileLoader
from langchain.chains.summarize import load_summarize_chain
from langchain.text_splitter import RecursiveCharacterTextSplitter
from langchain import OpenAI# 导入文本
loader = UnstructuredFileLoader("/content/sample_data/data/lg_test.txt")
# 将文本转成 Document 对象
document = loader.load()
print(f'documents:{len(document)}')
b. Document 文档(解决加载数据超过模型最大输入) 与 Text Spltters 文本分割

当使用loader加载器读取到数据源后,数据源需要转换成 Document 对象后,后续才能进行使用。
Text Spltters ,文本分割就是用来分割文本的。为什么需要分割文本?因为我们每次不管是做把文本当作 prompt 发给 openai api ,还是还是使用 openai api embedding 功能都是有字符限制的。

#示例:from langchain.document_loaders import UnstructuredFileLoader
from langchain.chains.summarize import load_summarize_chain
from langchain.text_splitter import RecursiveCharacterTextSplitter
from langchain import OpenAI# 导入文本
loader = UnstructuredFileLoader("/content/sample_data/data/lg_test.txt")
# 将文本转成 Document 对象
document = loader.load()
print(f'documents:{len(document)}')# 初始化文本分割器
text_splitter = RecursiveCharacterTextSplitter(chunk_size = 500,chunk_overlap = 0
)# 切分文本
split_documents = text_splitter.split_documents(document)
print(f'documents:{len(split_documents)}')# 加载 llm 模型
llm = OpenAI(model_name="text-davinci-003", max_tokens=1500)# 创建总结链
chain = load_summarize_chain(llm, chain_type="refine", verbose=True)# 执行总结链,(为了快速演示,只总结前5段)
chain.run(split_documents[:5])

这里有几个参数需要注意:

  1. 文本分割器的 chunk_overlap 参数
    这个是指切割后的每个 document 里包含几个上一个 document 结尾的内容,主要作用是为了增加每个 document 的上下文关联。比如,chunk_overlap=0时, 第一个 document 为 aaaaaa,第二个为 bbbbbb;当 chunk_overlap=2 时,第一个 document 为 aaaaaa,第二个为 aabbbbbb。

  2. chain 的 chain_type 参数

这个参数主要控制了将 document 传递给 llm 模型的方式,一共有 4 种方式:
stuff: 这种最简单粗暴,会把所有的 document 一次全部传给 llm 模型进行总结。如果document很多的话,势必会报超出最大 token 限制的错,所以总结文本的时候一般不会选中这个。
map_reduce: 这个方式会先将每个 document 进行总结,最后将所有 document 总结出的结果再进行一次总结。
refine: 这种方式会先总结第一个 document,然后在将第一个 document 总结出的内容和第二个 document 一起发给 llm 模型在进行总结,以此类推。这种方式的好处就是在总结后一个 document 的时候,会带着前一个的 document 进行总结,给需要总结的 document 添加了上下文,增加了总结内容的连贯性
map_rerank: 这种一般不会用在总结的 chain 上,而是会用在问答的 chain 上,他其实是一种搜索答案的匹配方式。首先你要给出一个问题,他会根据问题给每个 document 计算一个这个 document 能回答这个问题的概率分数,然后找到分数最高的那个 document ,在通过把这个 document 转化为问题的 prompt 的一部分(问题+document)发送给 llm 模型,最后 llm 模型返回具体答案。

d. Vectorstores 向量数据库

因为数据相关性搜索其实是向量运算。所以,不管我们是使用 openai api embedding 功能还是直接通过向量数据库直接查询,都需要将我们的加载进来的数据 Document 进行向量化,才能进行向量运算搜索。转换成向量也很简单,只需要我们把数据存储到对应的向量数据库中即可完成向量的转换。
官方也提供了很多的向量数据库供我们使用。

#示例:
from langchain.vectorstores import Chroma# 持久化数据
docsearch = Chroma.from_documents(documents, embeddings, persist_directory="D:/vector_store")
docsearch.persist()# 加载数据
docsearch = Chroma(persist_directory="D:/vector_store", embedding_function=embeddings)
e. Embedding

用于衡量文本的相关性。这个也是 OpenAI API 能实现构建自己知识库的关键所在。
他相比 fine-tuning 最大的优势就是,不用进行训练,并且可以实时添加新的内容,而不用加一次新的内容就训练一次,并且各方面成本要比 fine-tuning 低很多。

5. Memory:记住以前的对话

使用Memory实现一个带记忆的对话机器人

from langchain.memory import ChatMessageHistory
from langchain.chat_models import ChatOpenAIchat = ChatOpenAI(temperature=0)# 初始化 MessageHistory 对象
history = ChatMessageHistory()# 给 MessageHistory 对象添加对话内容
history.add_ai_message("你好!")
history.add_user_message("中国的首都是哪里?")# 执行对话
ai_response = chat(history.messages)
print(ai_response)

6. Agents:访问其他工具,自定义agent中所使用的工具

自定义agent中所使用的工具

from langchain.agents import initialize_agent, Tool
from langchain.agents import AgentType
from langchain.tools import BaseTool
from langchain.llms import OpenAI
from langchain import LLMMathChain, SerpAPIWrapperllm = OpenAI(temperature=0)# 初始化搜索链和计算链
search = SerpAPIWrapper()
llm_math_chain = LLMMathChain(llm=llm, verbose=True)# 创建一个功能列表,指明这个 agent 里面都有哪些可用工具,agent 执行过程可以看必知概念里的 Agent 那张图
tools = [Tool(name = "Search",func=search.run,description="useful for when you need to answer questions about current events"),Tool(name="Calculator",func=llm_math_chain.run,description="useful for when you need to answer questions about math")
]# 初始化 agent
agent = initialize_agent(tools, llm, agent=AgentType.ZERO_SHOT_REACT_DESCRIPTION, verbose=True)# 执行 agent
agent.run("Who is Leo DiCaprio's girlfriend? What is her current age raised to the 0.43 power?")

三、经典示例

1. 最简单的交互

用 LangChain 加载 OpenAI 的模型,并且完成一次问答。我们需要先设置我们的 openai 的 key,这个 key 可以在用户管理里面创建。

import os
os.environ["OPENAI_API_KEY"] = '你的api key'
然后,我们进行导入和执行
from langchain.llms import OpenAIllm = OpenAI(model_name="text-davinci-003",max_tokens=1024)
llm("怎么评价人工智能")

2. 构建本地知识库问答机器人

从本地读取多个文档构建知识库,并且使用 Openai API 在知识库中进行搜索并给出答案。

from langchain.embeddings.openai import OpenAIEmbeddings
from langchain.vectorstores import Chroma
from langchain.text_splitter import CharacterTextSplitter
from langchain import OpenAI
from langchain.document_loaders import DirectoryLoader
from langchain.chains import RetrievalQA# 加载文件夹中的所有txt类型的文件
loader = DirectoryLoader('/content/sample_data/data/', glob='**/*.txt')
# 将数据转成 document 对象,每个文件会作为一个 document
documents = loader.load()# 初始化加载器
text_splitter = CharacterTextSplitter(chunk_size=100, chunk_overlap=0)
# 切割加载的 document
split_docs = text_splitter.split_documents(documents)# 初始化 openai 的 embeddings 对象
embeddings = OpenAIEmbeddings()
# 将 document 通过 openai 的 embeddings 对象计算 embedding 向量信息并临时存入 Chroma 向量数据库,用于后续匹配查询
docsearch = Chroma.from_documents(split_docs, embeddings)# 创建问答对象
qa = RetrievalQA.from_chain_type(llm=OpenAI(), chain_type="stuff", retriever=docsearch.as_retriever(), return_source_documents=True)
# 进行问答
result = qa({"query": "科大讯飞今年第一季度收入是多少?"})
print(result)

3. 让输出内容 结构化起来

from langchain.output_parsers import StructuredOutputParser, ResponseSchema
from langchain.prompts import PromptTemplate
from langchain.llms import OpenAIllm = OpenAI(model_name="text-davinci-003")# 告诉他我们生成的内容需要哪些字段,每个字段类型式啥
response_schemas = [ResponseSchema(name="bad_string", description="This a poorly formatted user input string"),ResponseSchema(name="good_string", description="This is your response, a reformatted response")
]# 初始化解析器
output_parser = StructuredOutputParser.from_response_schemas(response_schemas)# 生成的格式提示符
# {
#	"bad_string": string  // This a poorly formatted user input string
#	"good_string": string  // This is your response, a reformatted response
#}
format_instructions = output_parser.get_format_instructions()template = """
You will be given a poorly formatted string from a user.
Reformat it and make sure all the words are spelled correctly{format_instructions}% USER INPUT:
{user_input}YOUR RESPONSE:
"""# 将我们的格式描述嵌入到 prompt 中去,告诉 llm 我们需要他输出什么样格式的内容
prompt = PromptTemplate(input_variables=["user_input"],partial_variables={"format_instructions": format_instructions},template=template
)promptValue = prompt.format(user_input="welcom to califonya!")
llm_output = llm(promptValue)# 使用解析器进行解析生成的内容
output_parser.parse(llm_output)

4. 使用 Hugging Face 模型

#使用 Hugging Face 模型之前,需要先设置环境变量
import os
os.environ['HUGGINGFACEHUB_API_TOKEN'] = ''
  1. 使用在线的 Hugging Face 模型
from langchain import PromptTemplate, HuggingFaceHub, LLMChaintemplate = """Question: {question}
Answer: Let's think step by step."""prompt = PromptTemplate(template=template, input_variables=["question"])
llm = HuggingFaceHub(repo_id="google/flan-t5-xl", model_kwargs={"temperature":0, "max_length":64})
llm_chain = LLMChain(prompt=prompt, llm=llm)question = "What NFL team won the Super Bowl in the year Justin Beiber was born?"
print(llm_chain.run(question))
  1. 将 Hugging Face 模型直接拉到本地使用
from langchain import PromptTemplate, LLMChain
from langchain.llms import HuggingFacePipeline
from transformers import AutoTokenizer, AutoModelForCausalLM, pipeline, AutoModelForSeq2SeqLMmodel_id = 'google/flan-t5-large'
tokenizer = AutoTokenizer.from_pretrained(model_id)
model = AutoModelForSeq2SeqLM.from_pretrained(model_id)pipe = pipeline("text2text-generation",model=model,tokenizer=tokenizer,max_length=100
)local_llm = HuggingFacePipeline(pipeline=pipe)
print(local_llm('What is the capital of France? '))template = """Question: {question} Answer: Let's think step by step."""
prompt = PromptTemplate(template=template, input_variables=["question"])llm_chain = LLMChain(prompt=prompt, llm=local_llm)
question = "What is the capital of England?"
print(llm_chain.run(question))

将模型拉到本地使用的好处:
训练模型
可以使用本地的 GPU
有些模型无法在 Hugging Face 运行

4. 通过自然语言执行SQL命令

我们通过 SQLDatabaseToolkit 或者 SQLDatabaseChain 都可以实现执行SQL命令的操作

from langchain.agents import create_sql_agent
from langchain.agents.agent_toolkits import SQLDatabaseToolkit
from langchain.sql_database import SQLDatabase
from langchain.llms.openai import OpenAIdb = SQLDatabase.from_uri("sqlite:///../notebooks/Chinook.db")
toolkit = SQLDatabaseToolkit(db=db)agent_executor = create_sql_agent(llm=OpenAI(temperature=0),toolkit=toolkit,verbose=True
)agent_executor.run("Describe the playlisttrack table")
from langchain import OpenAI, SQLDatabase, SQLDatabaseChaindb = SQLDatabase.from_uri("mysql+pymysql://root:root@127.0.0.1/chinook")
llm = OpenAI(temperature=0)db_chain = SQLDatabaseChain(llm=llm, database=db, verbose=True)
db_chain.run("How many employees are there?")

参考文献
[1].https://blog.csdn.net/lht0909/article/details/130412875
[2].https://blog.csdn.net/v_JULY_v/article/details/131552592
[3].https://developer.aliyun.com/article/1221923
[4].https://liaokong.gitbook.io/llm-kai-fa-jiao-cheng/#jie-gou-hua-shu-chu

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/135388.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

使用LogBack替换Log4j

目录 1.删除log4j有关的依赖&#xff0c;添加logBack依赖 2.删除log4j配置文件&#xff0c;增加logback.xml配置文件 3.更改application.yml配置文件&#xff0c;log文件指向logback.xml 4.重启 1.删除log4j有关的依赖&#xff0c;添加logBack依赖 <dependency><gr…

掌动智能:云可观测性的主要特点及应用场景

云全景可观测性安全平台是一个跨架构、跨平台的可观测性方案&#xff0c;实现对云环境下的细粒度数据可视化&#xff0c;满足安全部门对云内部安全领域的多场景诉求&#xff0c;包括敏感数据动态监管、云网攻击回溯分析、攻击横移风险监控、云异常流量分析。本文将介绍掌动智能…

关于使用es数组的改变方式

一&#xff09;改变原数组的方法&#xff08;9个&#xff09; ES5&#xff1a; 1. pop() 删除一个数组中的最后的一个元素&#xff0c;并且返回这个元素。 2.shift() 删除数组的第一个元素&#xff0c;并返回这个元素。 3.push() 可向数组的末尾添加一个或多个元素&#xf…

【Nginx39】Nginx学习:upstream服务器组模块

Nginx学习&#xff1a;upstream服务器组模块 最后一个重点模块内容啦&#xff0c;感谢坚持到现在的你和我。总算是向大佬的道路上又前进了一步了。今天的内容主要是服务器组的配置&#xff0c;其实更直白点&#xff0c;就是 Nginx 负载均衡的配置模块。会不会有小伙伴不明白负载…

kubernetes集群编排(8)

k8s资源监控 资源限制 上传镜像 [rootk8s2 limit]# vim limit.yaml apiVersion: v1 kind: Pod metadata:name: memory-demo spec:containers:- name: memory-demoimage: stressargs:- --vm- "1"- --vm-bytes- 200Mresources:requests:memory: 50Milimits:memory: 100…

04-react基础知识-路由

一、react路由环境安装 使用指令&#xff1a;npm i --save react-router-dom type/react-router-dom进行react路由环境安装 二、引入路由 在main.jsx文件中引入该语句&#xff1a; import { createBrowserRouter, RouterProvider } from react-router-dom 定义一个变量rou…

【Java笔试强训】Day9(CM72 另类加法、HJ91 走方格的方案数)

CM72 另类加法 链接&#xff1a;另类加法 题目&#xff1a; 给定两个int A和B。编写一个函数返回AB的值&#xff0c;但不得使用或其他算数运算符。 题目分析&#xff1a; 代码实现&#xff1a; package Day9;public class Day9_1 {public int addAB(int A, int B) {// wr…

「Verilog学习笔记」使用子模块实现三输入数的大小比较

专栏前言 本专栏的内容主要是记录本人学习Verilog过程中的一些知识点&#xff0c;刷题网站用的是牛客网 分析 题目要求编写子模块实现两个输入数的大小比较并输出较小值&#xff0c;可以使用if-else语句实现。同时要求在主模块中实现三个输入数值的大小比较&#xff0c;假设三个…

【配置】如何在打包Spring Boot项目时按需使用日常、测试、预发、正式环境的配置文件

文章目录 前言1. 创建5个配置文件2. 在pom.xml文件中如下配置3. 在application.properties中加入环境变量 前言 在我们开发项目的时候&#xff0c;一般有四套环境&#xff1a;日常、测试、预发、正式。日常环境作为我们开发环境&#xff1b;测试环境给测试同学测试功能&#x…

AI诈骗的防范与应对:维护数字安全的责任

近年来&#xff0c;人工智能生成内容&#xff08;AIGC&#xff09;技术在各个领域都取得了显著的进展&#xff0c;为我们带来了更多的便捷和创新。然而&#xff0c;与此同时&#xff0c;这项技术也被不法分子滥用&#xff0c;用于实施各种形式的AI诈骗。这种威胁需要我们认真对…

​软考-高级-信息系统项目管理师教程 第四版【第21章-项目管理科学基础-思维导图】​

软考-高级-信息系统项目管理师教程 第四版【第21章-项目管理科学基础-思维导图】 课本里章节里所有蓝色字体的思维导图

抽象方法及接口的使用概念

abstract关键字 /* * 类和对象&#xff1a; * 类&#xff1a;一个概念&#xff0c;客观不存在的&#xff0c;或者认为是一个模板。 * 对象&#xff1a;看得见摸得着的真实存在的物体。 * 对象---类的过程&#xff0c;抽象 * 类---对象的过程&#xff0c;叫实例化 * 抽…

oracle查询前几条数据的方法

在Oralce中实现select top N&#xff1a;由于Oracle不支持select top 语句&#xff0c;所以在oracle中经常是用order by 跟rownum的组合来实现select top n的查询。 方法1&#xff1a; SELECT * FROM (SELECT * FROM EMP ORDER BY SAL DESC) WHERE ROWNUM < 5 --抽取处记录…

【elasticsearch+kibana基于windows docker安装】

创建网络&#xff1a;es和kibana容器互联 docker network create es-net加载镜像 docker pull elasticsearch:7.12.1运行 docker run -d --name es -p 9200:9200 -p 9300:9300 -e "discovery.typesingle-node" -e ES_JAVA_OPTS"-Xms512m -Xmx512m" -v $…

uni-app基于vue实现商城小程序

一、前言 参考“网易严选”小程序 项目采用传统vue项目结构&#xff0c;即uni-app打包和运行成小程序&#xff0c;使用HBuilder开发工具开发项目&#xff0c;通过运行启动“微信开发者工具”完成项目启动。 二、功能效果图 1.首页 2.分类 3.活动 4.我的 5.商品详情 6.购物车…

React中组件之间如何通信?

一、是什么 我们将组件间通信可以拆分为两个词&#xff1a; 组件通信 回顾Vue系列的文章&#xff0c;组件是vue中最强大的功能之一&#xff0c;同样组件化是React的核心思想 相比vue&#xff0c;React的组件更加灵活和多样&#xff0c;按照不同的方式可以分成很多类型的组件…

第五届泰迪杯数据分析技能赛B题源码图片分享

需要B题源码以及第六届带队”指导“请私信本人&#xff0c;团队包含技能赛双一等&#xff0c;数学建模省一&#xff0c;泰迪杯挖掘国一&#xff0c;研究生队友。 去年一等作品可视化图如下&#xff0c;私信获取源码

【Ruoyi管理后台】用户登录强制修改密码

近期有个需求&#xff0c;就是需要调整Ruoyi管理后台&#xff1a;用户如果三个月(长时间)未修改过密码&#xff0c;需要在登录时强制修改密码&#xff0c;否则不能登录系统。 一、后端项目调整 从需求来看&#xff0c;我们需要在用户表增加一个字段&#xff0c;用于标记用户最…

【C语言】动态内存管理

大家好&#xff0c;我是苏貝&#xff0c;本篇博客带大家了解动态内存管理&#xff0c;如果你觉得我写的还不错的话&#xff0c;可以给我一个赞&#x1f44d;吗&#xff0c;感谢❤️ 目录 一. 为什么存在动态内存分配二. 动态内存函数的介绍2.1 malloc和free2.2 calloc2.3 real…

Linux/centos上如何配置管理Web服务器?

Linux/centos上如何配置管理Web服务器&#xff1f; 1 Web简单了解2 关于Apache3 如何安装Apache服务器&#xff1f;3.1 Apache服务安装3.2 httpd服务的基本操作 4 如何配置Apache服务器&#xff1f;4.1 关于httpd.conf配置4.2 常用指令 5 简单实例 1 Web简单了解 Web服务器称为…