Spring AI 第二讲 之 Chat Model API 第六节Google VertexAI API

VertexAI API 可提供高质量的定制机器学习模型,只需花费最少的机器学习专业知识和精力。
Spring AI 通过以下客户端提供与 VertexAI API 的集成:

VertexAI Gemini Chat

Vertex AI Gemini API 允许开发人员使用 Gemini 模型构建生成式人工智能应用程序。Vertex AI 双子座应用程序接口支持作为输入和输出文本或代码的多模态提示。多模态模型是一种能够处理来自图像、视频和文本等多种模态信息的模型。例如,您可以向模型发送一盘曲奇饼干的照片,并要求它为您提供这些曲奇饼干的食谱。

双子座

双子座 API 参考

前提条件

设置 Java 开发环境。运行以下命令进行身份验证。将 PROJECT_ID 替换为您的 Google Cloud 项目 ID,将 ACCOUNT 替换为您的 Google Cloud 用户名。

gcloud config set project PROJECT_ID &&
gcloud auth application-default login ACCOUNT

自动配置

Spring AI 为 VertexAI Gemini Chat Client 提供 Spring Boot 自动配置功能。要启用它,请在项目的 Maven pom.xml 文件中添加以下依赖项:

<dependency><groupId>org.springframework.ai</groupId><artifactId>spring-ai-vertex-ai-gemini-spring-boot-starter</artifactId>
</dependency>

或 Gradle build.gradle 构建文件。

dependencies {implementation 'org.springframework.ai:spring-ai-vertex-ai-gemini-spring-boot-starter'
}

请参阅 "依赖关系管理 "部分,将 Spring AI BOM 添加到构建文件中。

聊天属性

spring.ai.vertex.ai.gemini 前缀是用于连接 VertexAI 的属性前缀。

属性属性默认值

spring.ai.vertex.ai.gemini.projectId

谷歌云平台项目 ID

-

spring.ai.vertex.ai.gemini.location

地区

-

spring.ai.vertex.ai.gemini.credentialsUri

Vertex AI Gemini 凭据的 URI。如果提供,它将用于创建一个 GoogleCredentials 实例来验证 VertexAI。

-

spring.ai.vertex.ai.gemini.apiEndpoint

Vertex AI Gemini API 端点。

-

spring.ai.vertex.ai.gemini.scope

-

spring.ai.vertex.ai.gemini.transport

API 传输。GRPC 或 REST。

GRPC

spring.ai.vertex.ai.gemini.chat 前缀是用于配置 VertexAI Gemini Chat 聊天模型实现的属性前缀。

属性说明默认值

spring.ai.vertex.ai.gemini.chat.options.model

支持使用的 Vertex AI 双子座聊天模型包括(1.0)gemini-pro、gemini-pro-vision 和新的(1.5)gemini-1.5-pro-preview-0514、gemini-1.5-flash-preview-0514 模型。

gemini-pro

spring.ai.vertex.ai.gemini.chat.options.temperature

控制输出的随机性。取值范围为 [0.0,1.0](含 0.0)。数值越接近 1.0,生成的反应就越多变,而数值越接近 0.0,生成器的反应通常就越出人意料。该值指定后端在调用生成器时使用的默认值。

0.8

spring.ai.vertex.ai.gemini.chat.options.topK

采样时要考虑的最大标记数。生成器结合使用 Top-k 和核采样。Top-k 取样考虑前 K 个最有可能的标记集。

-

spring.ai.vertex.ai.gemini.chat.options.topP

采样时要考虑的标记的最大累积概率。生成器结合使用 Top-k 和核采样。核采样会考虑概率总和至少为 topP 的最小标记集。

-

spring.ai.vertex.ai.gemini.chat.options.candidateCount

要返回的已生成响应信息的数量。该值必须介于 [1 - 8] 之间(含)。默认为 1。

-

spring.ai.vertex.ai.gemini.chat.options.candidateCount

要返回的已生成响应信息的数量。该值必须介于 [1 - 8] 之间(包括 1 和 8)。默认为 1。

-

spring.ai.vertex.ai.gemini.chat.options.maxOutputTokens

要生成的最大标记数。

-

spring.ai.vertex.ai.gemini.chat.options.frequencyPenalty 频率惩罚

-

spring.ai.vertex.ai.gemini.chat.options.presencePenalty 属性惩罚。

-

spring.ai.vertex.ai.gemini.chat.options.functions

由函数名称标识的函数列表,用于在单个提示请求中启用函数调用。具有这些名称的函数必须存在于 functionCallbacks 注册表中。

-

所有以 spring.ai.vertex.ai.gemini.chat.options 为前缀的属性都可通过在提示调用中添加特定于请求的运行时选项在运行时重写。

运行时选项

VertexAiGeminiChatOptions.java 提供了温度、topK 等模型配置。

启动时,可使用 VertexAiGeminiChatModel(api, options) 构造函数或 Spring.ai.vertex.ai.chat.options.* 属性配置默认选项。

在运行时,您可以通过在提示调用中添加新的、针对特定请求的选项来覆盖默认选项。例如,覆盖特定请求的默认温度:

ChatResponse response = chatModel.call(new Prompt("Generate the names of 5 famous pirates.",VertexAiPaLm2ChatOptions.builder().withTemperature(0.4).build()));

除了特定于模型的 VertexAiChatPaLm2Options 之外,您还可以使用便携式 ChatOption

函数调用

截至 2023 年 4 月 30 日,Vertex AI Gemini Pro 模型已大幅降低了对函数调用的支持!虽然该功能仍然可用,但不建议在生产中使用。显然,Gemini Pro 无法再正确处理函数名称。并行函数调用功能也不复存在。

您可以在 VertexAiGeminiChatModel 上注册自定义 Java 函数,然后让 Gemini Pro 模型智能地选择输出一个包含参数的 JSON 对象,以调用一个或多个注册函数。这是一种将 LLM 功能与外部工具和 API 相连接的强大技术。了解有关顶点人工智能双子座函数调用的更多信息。

多模式

多模态是指模型同时理解和处理来自不同来源的信息的能力,包括

谷歌的双子座人工智能模型通过理解和整合文本、代码、音频、图像和视频来支持这种能力。更多详情,请参阅博文 "Gemini 介绍"。

Spring AI 的消息接口通过引入媒体类型支持多模态 AI 模型。该类型使用 Spring 的 org.springframework.util.MimeType 和用于原始媒体数据的 java.lang.Object 来包含有关消息中媒体附件的数据和信息。

下面是从 VertexAiGeminiChatModelIT.java 中提取的一个简单代码示例,演示了用户文本与图像的结合。

byte[] data = new ClassPathResource("/vertex-test.png").getContentAsByteArray();var userMessage = new UserMessage("Explain what do you see o this picture?",List.of(new Media(MimeTypeUtils.IMAGE_PNG, data)));ChatResponse response = chatModel.call(new Prompt(List.of(userMessage)));

示例控制器

创建一个新的 Spring Boot 项目,并将 spring-ai-vertex-ai-palm2-spring-boot-starter 添加到您的 pom(或 gradle)依赖项中。

在 src/main/resources 目录下添加 application.properties 文件,以启用和配置 VertexAi 聊天模型:

spring.ai.vertex.ai.gemini.project-id=PROJECT_ID
spring.ai.vertex.ai.gemini.location=LOCATION
spring.ai.vertex.ai.gemini.chat.options.model=vertex-pro-vision
spring.ai.vertex.ai.gemini.chat.options.temperature=0.5

将 api-key 替换为您的 VertexAI 凭据。

这将创建一个 VertexAiGeminiChatModel 实现,您可以将其注入到您的类中。下面是一个使用聊天模型生成文本的简单 @Controller 类的示例。

@RestController
public class ChatController {private final VertexAiGeminiChatModel chatModel;@Autowiredpublic ChatController(VertexAiGeminiChatModel chatModel) {this.chatModel = chatModel;}@GetMapping("/ai/generate")public Map generate(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {return Map.of("generation", chatModel.call(message));}@GetMapping("/ai/generateStream")public Flux<ChatResponse> generateStream(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {Prompt prompt = new Prompt(new UserMessage(message));return chatModel.stream(prompt);}
}

手动配置

VertexAiGeminiChatModel 实现了 ChatModel 并使用 VertexAI 连接到 Vertex AI Gemini 服务。

在项目的 Maven pom.xml 文件中添加 Spring-ai-vertex-ai-gemini 依赖关系:

<dependency><groupId>org.springframework.ai</groupId><artifactId>spring-ai-vertex-ai-gemini</artifactId>
</dependency>

或 Gradle build.gradle 构建文件中。

dependencies {implementation 'org.springframework.ai:spring-ai-vertex-ai-gemini'
}

请参阅 "依赖关系管理 "部分,将 Spring AI BOM 添加到构建文件中。

接下来,创建 VertexAiGeminiChatModel 并将其用于文本生成:

VertexAI vertexApi =  new VertexAI(projectId, location);var chatModel = new VertexAiGeminiChatModel(vertexApi,VertexAiGeminiChatOptions.builder().withModel(ChatModel.GEMINI_PRO_1_5_PRO).withTemperature(0.4).build());ChatResponse response = chatModel.call(new Prompt("Generate the names of 5 famous pirates."));

VertexAiGeminiChatOptions 为聊天请求提供配置信息。VertexAiGeminiChatOptions.Builder 是流畅的选项生成器。

底层 Java 客户端

下面的类图说明了 Vertex AI Gemini 本地 Java API:

vertex ai gemini native api

VertexAI PaLM2 功能调用

Gemini Function Calling

警告:显然,Gemini Pro 无法再正确处理函数名称。并行函数调用也已消失。

函数调用允许开发人员在代码中创建函数描述,然后在请求中将该描述传递给语言模型。模型的响应包括符合描述的函数名称以及调用该函数的参数。

您可以向 VertexAiGeminiChatModel 注册自定义 Java 函数,然后让 Gemini Pro 模型智能地选择输出包含参数的 JSON 对象,以调用一个或多个已注册函数。这样,您就可以将 LLM 功能与外部工具和 API 相连接。VertexAI Gemini Pro 模型经过训练,能够检测函数何时应被调用,并以符合函数签名的 JSON 响应。

VertexAI Gemini API 不会直接调用函数;相反,模型会生成 JSON,您可以用它在代码中调用函数,并将结果返回给模型以完成对话。

Spring AI 提供了灵活、用户友好的注册和调用自定义函数的方法。一般来说,自定义函数需要提供函数名称、描述和函数调用签名(如 Open API 模式),以便让模型知道函数期望使用哪些参数。描述有助于模型了解何时调用函数。

作为开发人员,您需要实现一个函数,接收人工智能模型发送的函数调用参数,并将结果反馈给模型。您的函数可以反过来调用其他第三方服务来提供结果。

Spring AI 将此变得非常简单,只需定义一个 @Bean 定义,返回一个 java.util.Function 并在调用 ChatModel 时提供 bean 名称作为选项即可。

在引擎盖下,Spring 会用适当的适配器代码封装您的 POJO(函数),从而实现与 AI 模型的交互,使您无需编写繁琐的模板代码。底层基础架构的基础是 FunctionCallback.java接口和配套的 FunctionCallbackWrapper.java实用程序类,用于简化 Java 回调函数的实现和注册。

工作原理

假设我们想让人工智能模型响应它所不具备的信息,例如给定地点的当前温度。

我们可以向人工智能模型提供有关我们自身功能的元数据,让它在处理您的提示时可以用来检索这些信息。

例如,如果在处理提示时,人工智能模型确定它需要有关给定地点温度的额外信息,它就会启动服务器端生成的请求/响应交互。人工智能模型会调用客户端函数。AI 模型以 JSON 格式提供方法调用细节,客户端负责执行该函数并返回响应。

Spring AI 大大简化了为支持函数调用而编写的代码。它为您提供函数调用对话的中介。您只需以 @Bean 的形式提供函数定义,然后在提示选项中提供函数的 Bean 名称即可。您还可以在提示中引用多个函数 Bean 名称。

快速入门

让我们创建一个聊天机器人,通过调用自己的函数来回答问题。为了支持聊天机器人的回复,我们将注册自己的函数,该函数接收一个地点并返回该地点的当前天气。

当需要回答诸如 "波士顿的天气如何?"这样的问题时,人工智能模型将调用客户端,提供位置值作为参数传递给函数。这种类似 RPC 的数据以 JSON 格式传递。

我们的函数可以使用基于 SaaS 的天气服务 API,并将天气响应返回给模型,以完成对话。在本示例中,我们将使用一个名为 MockWeatherService 的简单实现,对不同地点的温度进行硬编码。
下面的 MockWeatherService.java 表示天气服务 API:

public class MockWeatherService implements Function<Request, Response> {public enum Unit { C, F }public record Request(String location, Unit unit) {}public record Response(double temp, Unit unit) {}public Response apply(Request request) {return new Response(30.0, Unit.C);}
}

将函数注册为 Bean

通过 VertexAiGeminiChatModel 自动配置,您有多种方法在 Spring 上下文中将自定义函数注册为 Bean。

我们首先介绍对 POJO 最友好的选项。

普通 Java 函数

在这种方法中,您可以在应用程序上下文中定义 @Beans,就像定义任何其他 Spring 托管对象一样。

在内部,Spring AI ChatModel 将创建一个 FunctionCallbackWrapper 封装器实例,该封装器添加了通过 AI 模型调用该函数的逻辑。@Bean 的名称将作为 ChatOption 传递。

@Configuration
static class Config {@Bean@Description("Get the weather in location") // function descriptionpublic Function<MockWeatherService.Request, MockWeatherService.Response> weatherFunction1() {return new MockWeatherService();}...
}

@Description 注解是可选的,它提供了一个函数描述 (2),帮助模型理解何时调用函数。这是一个需要设置的重要属性,可帮助人工智能模型确定要调用的客户端函数。

另一种提供函数说明的方法是在 MockWeatherService.Request 上使用 @JsonClassDescription 注解来提供函数说明:

@Configuration
static class Config {@Beanpublic Function<Request, Response> currentWeather3() { // (1) bean name as function name.return new MockWeatherService();}...
}@JsonClassDescription("Get the weather in location") // (2) function description
public record Request(String location, Unit unit) {}

最佳做法是为请求对象注释信息,使生成的函数 JSON 模式尽可能具有描述性,以帮助人工智能模型选择要调用的正确函数。

FunctionCallWithFunctionBeanIT.java演示了这种方法。

函数回调封装器

注册函数的另一种方法是创建一个 FunctionCallbackWrapper 封装器,如下所示:

@Configuration
static class Config {@Beanpublic FunctionCallback weatherFunctionInfo() {return FunctionCallbackWrapper.builder(new MockWeatherService()).withName("CurrentWeather") // (1) function name.withDescription("Get the current weather in a given location") // (2) function description.withSchemaType(SchemaType.OPEN_API) // (3) schema type. Compulsory for Gemini function calling..build();}...
}

它封装了第三方 MockWeatherService 函数,并将其注册为 VertexAiGeminiChatModel 的 CurrentWeather 函数。它还提供了说明 (2),并将模式类型设置为开放式 API 类型 (3)。

默认的响应转换器会对响应对象进行 JSON 序列化。

FunctionCallbackWrapper 会根据 MockWeatherService.Request 类在内部解析函数调用签名,并在内部为函数调用生成 Open API 模式。

在聊天选项中指定函数

要让模型知道并调用您的 CurrentWeather 函数,您需要在提示请求中启用该函数:

VertexAiGeminiChatModel chatModel = ...UserMessage userMessage = new UserMessage("What's the weather like in San Francisco, Tokyo, and Paris?");ChatResponse response = chatModel.call(new Prompt(List.of(userMessage),VertexAiGeminiChatOptions.builder().withFunction("CurrentWeather").build())); // (1) Enable the functionlogger.info("Response: {}", response);

上述用户问题将触发对 CurrentWeather 函数的 3 次调用(每个城市一次),最终响应将类似于下面这样:

以下是所请求城市的当前天气情况:
- 加利福尼亚州旧金山: 30.0°C
- 日本东京: 10.0°C
- 法国巴黎: 15.0°C

FunctionCallWithFunctionWrapperIT.java测试演示了这种方法。

使用 Prompt 选项注册/调用函数

除自动配置外,您还可以通过 Prompt 请求动态注册回调函数: 

VertexAiGeminiChatModel chatModel = ...UserMessage userMessage = new UserMessage("What's the weather like in San Francisco, Tokyo, and Paris?  Use Multi-turn function calling.");var promptOptions = VertexAiGeminiChatOptions.builder().withFunctionCallbacks(List.of(FunctionCallbackWrapper.builder(new MockWeatherService()).withName("CurrentWeather").withSchemaType(SchemaType.OPEN_API) // IMPORTANT!!.withDescription("Get the weather in location").build())).build();ChatResponse response = chatModel.call(new Prompt(List.of(userMessage), promptOptions));

在该请求的持续时间内,提示中注册的功能默认为启用。

这种方法允许根据用户输入动态选择要调用的不同函数。

FunctionCallWithPromptFunctionIT.java 集成测试提供了一个完整示例,说明如何在 VertexAiGeminiChatModel 中注册函数并在提示请求中使用该函数。

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

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

相关文章

Apollo9.0 PNC源码学习之Control模块(一)

0 前言 从planning的角度看control&#xff0c;首先需要了解的就是相关的数据接口&#xff0c;规划出的轨迹&#xff08;路径速度&#xff09;发给Control模块去执行 modules/planning/planning_component/planning_component.cc planning模块发布轨迹信息 planning_writer_ …

利用CSS隐藏HTML元素并插入替代内容

在创建一个支持切换阅读模式和答题模式的Anki问答题模板中&#xff0c;我创建了一个支持切换阅读模式和答题模式的问答题模板&#xff0c;该文最终利用JavaScript将Anki输出的向下箭头删除&#xff0c;并插入自定义的提示语。经过进一步测试&#xff0c;发现实现上述功能完全不…

Unity 从0开始编写一个技能编辑器_02_Buff系统的生命周期

工作也有一年了&#xff0c;对技能编辑器也有了一些自己的看法&#xff0c;从刚接触时的惊讶&#xff0c;到大量工作时觉得有一些设计的冗余&#xff0c;在到特殊需求的修改&#xff0c;运行效率低时的优化&#xff0c;技能编辑器在我眼中已经不再是神圣不可攀的存在的&#xf…

【微信小程序】开发环境配置

目录 小程序的标准开发模式&#xff1a; 注册小程序的开发账号 安装开发者工具 下载 设置外观和代理 第一个小程序 -- 创建小程序项目 查看项目效果 第一种&#xff1a;在模拟器上查看项目效果 项目的基本组成结构 小程序代码的构成 app.json文件 project.config…

燃料电池汽车践行者

前言 见《氢燃料电池技术综述》 见《燃料电池工作原理详解》 见《燃料电池发电系统详解》 见《燃料电池电动汽车详解》 见《氢燃料电池汽车行业发展》 现代汽车&#xff08;中国&#xff09; 现代汽车集团&#xff0c;自1998年成立氢燃料电池研发小组以来深耕氢燃料电池技术&am…

html+CSS+js部分基础运用19

1. 应用动态props传递数据&#xff0c;输出影片的图片、名称和描述等信息【要求使用props】&#xff0c;效果图如下&#xff1a; 2.在页面中定义一个按钮和一行文本&#xff0c;通过单击按钮实现放大文本的功能。【要求使用$emit()】 代码可以截图或者复制黏贴放置在“实验…

spring-data-mongodb版本兼容问题

spring-data-mongodb与mongodb驱动有兼容性问题&#xff0c;不匹配会报NoSuchMethod异常&#xff0c;mongodb的java驱动包在4.0之后由mongodb-java-driver更名为mongodb-driver-sync。 spring-data-mongodb包依赖中有mongodb-driver-core&#xff0c;但缺诸如MongoCollection等…

【C语言】文件操作(终卷)

前言 我们在上一卷中了解了顺序读写的函数&#xff0c;现在就让我们从随机读写的函数开始吧。 什么是随机读写&#xff1f; 就是想在哪个位置读或写都行&#xff0c;比较自由。文件打开时光标默认在起始位置。想从后面的某个部分读或写&#xff0c;就得让文件指针来到那个位…

VMware Fusion 如何增加linux硬盘空间并成功挂载

文章目录 0. 前言1. 增加硬盘空间2. 硬盘分区2.1 查看硬盘2.2 分区2.3 格式化2.4 挂载 3. 参考 0. 前言 如果发现虚拟机分配的硬盘不足&#xff0c;需要增加硬盘空间。本文教给大家如何增加硬盘空间并成功挂载。 查看当前硬盘使用情况&#xff1a; df -h可以看到&#xff0c…

什么是档案数字化管理

档案数字化管理指的是将传统的纸质档案转换为数字形式&#xff0c;并通过电子设备、软件和网络技术进行管理和存储的过程。 档案数字化管理包括以下几个步骤&#xff1a; 1. 扫描和数字化&#xff1a;将纸质档案通过扫描仪转换为数字图像或文档。可以使用OCR&#xff08;光学字…

[数据集][图像分类]人种黄种人白人黑人分类数据集970张4类别

数据集类型&#xff1a;图像分类用&#xff0c;不可用于目标检测无标注文件 数据集格式&#xff1a;仅仅包含jpg图片&#xff0c;每个类别文件夹下面存放着对应图片 图片数量(jpg文件个数)&#xff1a;970 分类类别数&#xff1a;4 类别名称:[“Asian”,“Caucasian”,“Indian…

什么是 AOF 重写?AOF 重写机制的流程是什么?

引言&#xff1a;在Redis中&#xff0c;持久化是确保数据持久性和可恢复性的重要机制之一。除了常见的RDB&#xff08;Redis Database&#xff09;持久化方式外&#xff0c;AOF&#xff08;Append Only File&#xff09;也是一种常用的持久化方式。AOF持久化通过记录Redis服务器…

基于Gabor小波特征提取和PSO-SVM的胃溃疡分类(MATLAB R2018a)

Gabor滤波器是在测不准原则下能够在时域和频域中唯一能取得最佳的联合分辨率函数&#xff08;测不准原则&#xff1a;是指在时域与频域中都要获得任何的测量精度那是不可能同时实现的&#xff0c;要使时域分辨率有所提高&#xff0c;必须牺牲频域的分辨率&#xff0c;反之亦然&…

Java | Leetcode Java题解之第134题加油站

题目&#xff1a; 题解&#xff1a; class Solution {public int canCompleteCircuit(int[] gas, int[] cost) {int n gas.length;int i 0;while (i < n) {int sumOfGas 0, sumOfCost 0;int cnt 0;while (cnt < n) {int j (i cnt) % n;sumOfGas gas[j];sumOfCos…

Polar Web【中等】search

Polar Web【中等】search Contents Polar Web【中等】search思路&探索首页一般注入方式 EXP&效果Payload 总结 思路&探索 见到题目标题&#xff0c;预测可能有目录扫描或者输入框查询数据之类情况&#xff0c;具体细节在破解过程中才能清楚 打开站点&#xff0c;显…

如何下载BarTender软件及详细安装步骤

BarTender是美国海鸥科技推出的一款优秀的条码打印软件&#xff0c;应用于 WINDOWS95 、 98 、 NT 、 XP 、 2000 、 2003 和 3.1 版本&#xff0c; 产品支持广泛的条形码码制和条形码打印机&#xff0c; 不但支持条形码打印机而且支持激光打印机&#xff0c;还为世界知名品牌条…

前端-a-date-picker如何设置禁选时间段

想要做到如图所示的效果&#xff0c;代码如下&#xff1a; 第一个是只能选择某一天&#xff0c;第二个是只能选择某一个时间段 <a-date-pickerv-model:value"record.onTimeStr":show-time"{ format: HH:mm }"valueFormat"YYYY-MM-DD HH:mm:ss&qu…

【RAG入门教程02】Langchian的Embedding介绍与使用

Embedding介绍 词向量是 NLP 中的一种表示形式&#xff0c;其中词汇表中的单词或短语被映射到实数向量。它们用于捕获高维空间中单词之间的语义和句法相似性。 在词嵌入的背景下&#xff0c;我们可以将单词表示为高维空间中的向量&#xff0c;其中每个维度对应一个特定的特征…

mm-qcamera-daemon主函数分析

目录 main函数核心 main函数核心 main函数的主要任务包含在一个do{ } while(1)循环中. while循环中主要是监听文件描述符,故mai函数是由文件的读写来进行驱动的。 所有的文件描述符被封装成结构体 read_fd_info_t.其定义如下&#xff1a; /** read_fd_info_t* type -- either …

拯救者Legion Y9000X IRX9 2024(83FD)原装出厂Windows11系统镜像下载

lenovo联想2024款拯救者Y9000X IRX9 笔记本电脑【83FD】OEM预装Win11系统安装包&#xff0c;恢复开箱状态&#xff0c;自带恢复重置还原功能 链接&#xff1a;https://pan.baidu.com/s/1i_sVcnXF4qgsuj02rebe-Q?pwdyefp 提取码&#xff1a;yefp 联想原装WIN11系统自带所有…