如何又快又好实现 Catalog 系统搜索能力?火山引擎 DataLeap 这样做

news2024/11/19 9:19:26

摘要

DataLeap 是火山引擎数智平台 VeDI 旗下的大数据研发治理套件产品,帮助用户快速完成数据集成、开发、运维、治理、资产、安全等全套数据中台建设,降低工作成本和数据维护成本、挖掘数据价值、为企业决策提供数据支撑。

火山引擎 DataLeap 的 Data Catalog 系统通过汇总和组织各种元数据,解决了数据生产者梳理数据、数据消费者找数和理解数的业务场景,其中搜索是 Data Catalog 的主要功能之一。本文详细介绍火山引擎 DataLeap 的 Data Catalog 系统搜索功能的设计与实现。

背景

Data Catalog 能够帮助大公司更好地梳理和管理自己的资产,是 Data-drvien 公司的重要平台。一个通用的 Data Catalog 平台通常包含元数据管理,搜索,血缘,标签,术语等功能。其中,搜索是 Data Catalog 的入口功能,承担着让用户“找到数”的主要能力。在火山引擎 DataLeap 的 Data Catalog 系统中,每天有 70%以上的用户会使用搜索功能。

功能要求

业界主要的 Augmented Data Catalog 需要支持 Google 一样的搜索体验来搜索数据资产,以满足不同角色的用户的找数需求。我们的系统也一样,搜索需要支持的主要功能包括:

  • 支持多种不同类型资产的搜索。目前系统中已经包含 15+种数据源,可以分为几大类:数仓表比如 Hive,看板,数据集,实时表,Topic,对象存储,分布式文件系统如 LasFS 等。带来的主要挑战是不同类型的资产,搜索的字段和权重有明显差异。

  • 支持个性化。目前系统的用户遍布整个公司,角色涵盖数据工程师,数据分析师,产品经理,项目经理,销售和数据科学家等等,需要完成的数据工作任务差异也比较大,比如数据开发,数据治理,BI,数据分析和机器学习等等,因此个性化对 Data Catalog 的搜索尤为重要。

  • 支持各种业务元数据的高级筛选。数据资产除了名称/别名/描述等字段,通常还会有一些业务元数据,如项目/业务域/负责人/负责人部门/标签/业务术语/生命周期状态等。通过支持指定业务元数据进行筛选,帮助用户减小搜索范围,更快搜到对应资产。

  • 支持秒级的实时性。这里的实时性是指元数据的变更需要在秒级别反映到 Data Catalog 的搜索里,例如新建表需要在操作完成后 1~2 秒内即能搜到相应的表,删除表需要不再显示在搜索结果中。原因是用户新建或更新资产后通常会到我们的系统上查看相应的变更是否生效。用户手动在浏览器操作搜索的时间通常是秒级,超过这个时间会给用户带来困惑,降低整个 Data Catalog 的使用体验。

  • 支持 Google 类似的搜索推荐(Type as you search)功能。搜索补全功能是搜索的一个导航功能,可以在用户键入内容时提示他们可以输入的相关内容,从而提高搜索精度。这个功能对响应速度有一定的要求,同时由于数据资产的特殊性,前缀相同的资产数量较多,因此也需要根据资产的热度进行一定的排序。

  • 支持多租户。我们的系统不仅供公司内部使用,也提供公有云服务,因此支持多租户也是搜索的一个 P0 需求。

  • 支持多语言。数据资产的名称/描述/标签/术语等需要支持多种语言,搜索的输入也可能是不同的语言,最常用的比如英文和中文。不同语言的分词,专有名词字典,文本特征等都会带来一些挑战。

个性化的综合搜索

为了满足上述需求,火山引擎 DataLeap 采用了个性化综合搜索的方案。区别于联合搜索(federated search),用户需要指定搜索的具体资产类型或在搜索结果页对不同的资产分栏显示,综合搜索(unified search)允许用户在一个搜索框中进行搜索输入而无需指定搜索的资产类型,同时,搜索服务会在同一个搜索结果页返回不同类型的相关资产,并根据匹配程度和用户的个性化数据进行混合排序。优势是能给不同的用户针对不同资产的搜索需求提供统一的搜索体验,同时提供了用户跨类型圈定资产的能力。另外,综合搜索使得我们可以在页面上进行标准化透出,从而我们可以从技术上进行搜索标准化,达到新数据源接入即可搜索。

架构

整体架构

我们的搜索系统使用了开源的搜索引擎 Elasticsearch 进行基础的文档检索(Recall 阶段),因此各种资产元数据会被存放到 Elasticsearch 中。整个系统包括 4 个主要的数据流程:

  1. 实时导入。资产元数据变更时相应的平台发出实时变更消息,Data Catalog 系统会消费变更消息,通过 ingestion 服务更新 Elasticsearch 中的文档,以此来达到搜索实时性秒级的需求。

  2. 离线导入。实时导入的过程中可能会遇到网络波动等不可控因素导致更新失败,因此需要定时的任务来检查和增量更新缺失的元数据。

  3. 用户行为记录。记录用户搜索点击日志,用来后续进行搜索的 Badcase review 和模型训练。这部分采用了前端埋点和服务端埋点结合的方式。前端埋点有成熟的内部框架,埋点数据流入离线数仓表,缺点是这部分数据要经过离线任务 T+1 才能使用。服务端埋点数据直接进入 Elasticsearch,即时可用,同时在不支持前端埋点的场景(如 ToB 场景),可以成为主要的埋点数据收集方式。

  4. 线上搜索服务。提供搜索相关的线上服务,在后文详细解释这部分。

服务架构

上图是线上搜索服务的主要组件图。整个搜索服务分为三个大的服务:搜索推荐服务、聚合服务和搜索服务。

  • 搜索推荐服务(Type as you search)。搜索推荐服务对性能有一定的要求,通常来说补全的请求完成时间不能超过 200ms,超过了用户就会有比较明显的延迟感。因此不能直接使用搜索接口实现,我们的系统里是基于 Elasticsearch 的 Context suggester 实现的。除此之外,还有两个问题需要重点考虑:

  1. 基于浏览的热度排序。页面上能够推荐的词数是有限的,通常是 10 个,在输入较短时,候选的推荐词通常会超过这个限制,因此通过资产的浏览热度来排序可以提高搜索推荐的准确率,改善用户的搜索体验。

  2. 时序问题。一次搜索过程中会有一连串的搜索推荐请求,服务端会并行的处理这些请求,通常更长的输入由于候选推荐词更少服务端响应反而更快,在用户输入较快的时候(比如连续的删除字符),前端先发出的请求可能会后返回,因此可能造成输入停止后推荐的词与输入不匹配。我们的方案是前端在根据服务端响应刷新数据时需要检查返回的输入与当前输入框内容是否一致,从而保持最终一致性。

  • 聚合服务。聚合服务根据输入和筛选项提供搜索过程中需要用到的统计数字。例如用户希望知道搜索结果总共有多少条,每个筛选项下有多少个候选结果等统计信息,从而指导用户对搜索结果进行筛选,缩小搜索范围。同时,每个筛选项下的可选项需要根据输入和其它关联的筛选值动态生成,这部分也需要聚合服务提供。

  • 搜索服务。支持核心的搜索过程,通过输入,返回对应的资产作为搜索结果。分为 4 个主要的部分。

A:预处理过程(Preprocess),主要包含对输入的预处理和用户信息的预处理。

  1. 对输入的预处理主要包括分词,停用,词性还原等基本的文本处理。分词主要包含英文分词和中文分词。英文分词需要处理-_等链接符分词,中文分词主要是用 IK 分词器。停用主要包含各种词如“的”,“了”,“我”和各种特殊符号“》〉?”等无意义的词语。词性还原是一把双刃剑,因为 Data Catalog 中的词语不同于一般的自然语言,有比较多的专有名词,比如 live listing 不应当被还原为 live list,避免文本匹配的分数不准。同时这部分也包含对输入中的强 pattern 进行识别,如"数据库名.表名”等。

  2. 对用户信息的预处理。用户是否为超级用户,是否为 API 用户等,可以借此判断用户常搜索的资产类型或从未搜索的资产类型。

B:召回过程(Recall),负责通过输入和筛选项根据文本相关度从 Elasticsearch 查询一定数量的搜索候选结果,供下一步精排使用。召回过程需要保证用户期望的结果包含在召回结果中,否则后续排序优化都是徒劳。同时,召回的数量需要限制在合理的数值。主要原因有两点:一是排序靠后的搜索结果几乎没有用户会查看。二是召回过多的候选结果会影响性能,尤其是排序性能消耗比较大时。我们的召回主要分为两种方式:自然召回和强规则召回。

  1. 自然召回。对经过预处理的输入进行不同资产类型的召回,使用 best field 的策略,对资产的不同字段设置不同的权重,例如命中名称的资产应当比命中描述的资产优先级高。这里的权重通常根据经验设置,可以根据搜索结果的 Badcase review 得到,这个权重数值的精度要求不高,确保期望的结果能召回回来即可。

  2. 强规则召回。可以定制一些规则,作为自然召回的补充,涵盖精确表名的召回,或者从用户的常用资产列表进行召回。

 除此之外,还需要做好多租户的隔离,避免当前租户的用户召回其它租户的资产。

C:精排过程(Rank),负责对召回的结果进行最终的排序。精排过程依次包含机器学习模型预测(Learning to rank)和基于规则调整两部分。Learning to rank 部分详细介绍见后文。

  • 机器学习模型在线预测,负责主要的排序工作。加载离线训练得到的 PMML 模型文件,提供预测功能。

    基于强规则的调整,包含排序的各种兜底策略,比较常用的有:

    精确匹配的结果排在第一位。

    添加 Tie-breaker,保证分数相同的结果多次搜索的排序一致。

D:后处理过程(Postprocess),对排好序的结果添加各种不影响顺序的后处理。例如:

  • 权限检查,隐藏表设置。一些资产不希望被没有相关权限的用户查看详情,需要在搜索结果中设置相应字段并返回给前端。

    高亮,对命中字段进行高亮标注,返回给前端。

Learning to rank

Learning to rank 主要分为数据收集,离线训练和在线预测三个部分。搜索系统是一个 Data-driven system,因此系统设计之初就需要考虑数据收集。收集的数据可以用来评估和提升搜索的效果。数据收集和在线预测前面已有介绍,不再赘述,下面主要介绍离线训练部分。

离线训练的过程主要包括数据标注,特征工程,模型训练和评估。这四个步骤并非从前往后一气呵成,而是有可能进行评估,发现不足,然后增加标注数据,增加特征,重新训练,再次评估。评估效果有比较明显的收益时,才会上线测试。

数据标注

作为 Data Catalog 的搜索系统,不太容易获取大规模的人工标注数据,主要有两个原因:一是标注的成本较高,二是领域知识的专业性导致不容易找到合适的标注人员。因此,我们的标注数据来源主要有两个:一是来自搜索日志中有点击的部分,我们将这部分数据划分为三档,曝光有点击,曝光排名前五且未点击和曝光未点击,赋予不同的分数;二是我们根据资产名称结合日志中未点击的输入,基于规则生成一定的训练数据。

训练数据集需要持续更新,在 review badcase 时,可以针对需要改进的场景添加相应的训练数据。

特征

特征工程是一个持续的过程。经过一系列的选取,我们系统的主要特征分为 4 大类型,涵盖了搜索的文本特征,数据的权威性,用户的个性化数据和数据的时效性。

下面列举了一些我们用到的主要特征和分类:

  • 文本特征

  1. 输入相关的文本特征

  • 输入长度,比如有多少个词,总长度等等

  • 输入语言类型,中文或英文

  1. 文本匹配度相关的特征

  • 基于词袋的 CQR

  • Elasticsearch 查询返回分数,基于 BM25

  • 数据权威性

  1. 热度:AssetRank, 基于资产的使用量和血缘关系,通过 Weighted PageRank 算法计算得到的资产热度

  2. 元数据完整度,包含资产的业务元数据,如项目,主题,产品线等

  3. 资产的最近 1 天/7 天/30 天的全平台使用总次数

  4. 资产所处的生命周期:如上线,待下线,废弃等

  5. 资产的总点赞数

  • 用户个性化数据,分为三大类

  1. 静态个性化数据

  • 负责人:当前用户是否是该资产的负责人

    收藏:当前用户是否收藏了该资产

    点赞:当前用户是否点赞了该资产
    2.历史搜索查询行为数据

  • 当前用户历史上最近 1 天/7 天/30 天全平台使用该资产的次数

    当前用户历史上最近 1 天/7 天/30 天在 Data Catalog 平台查询点击该资产的次数
    3.协同数据

  • 同部门人员历史上最近 1 天/7 天/30 天在 Data Catalog 平台查询点击该资产的次数

    当前用户历史上最近 1 天/7 天/30 天在 Data Catalog 平台查询点击该资产所属部门所有资产的次数

    当前用户历史上最近 1 天/7 天/30 天在 Data Catalog 平台查询点击该资产所属负责人所有资产的次数

  • 数据时效性,用户会更倾向于使用最近创建或者有数据更新的资产

资产创建时间

资产数据的最近更新时间等

模型

Learning to rank 通常有三类方法:Pointwise,Pairwise 和 Listwise。这三类方法各有优缺点,细节介绍如下:

  • Pointwise,对每个输入,对每个召回的资产单独打分(通常是 Regression),然后按照分数进行排序。

优点:简单直观。

缺点:排序实际上不需要对资产进行精确打分,这类方法没有考虑召回资产之间的互相关系,考虑到用户在一组资产中只会点击其中一个,排名靠后的和排名靠前的资产在损失函数上的贡献没有体现。

  • Pairwise,对每个输入,考虑召回结果中所有资产的二元组合<资产 1, 资产 2>, 采取分类模型,预测两个资产的相对排序关系。

优点:基于点击与原有相关性分数排序标注简单,相比 pointwise 考虑到选项之间关系。

缺点:同样没有考虑排序前后顺序的重要性不同,样本生成复杂,开销大。对异常标注敏感,错误点影响范围大。

  • Listwise,考虑给定输入下的召回资产集合的整体序列,优化整个序列,通常使用 NDCG 作为优化目标。

优点:优化整个序列,考虑序列内资产之间的关系。

缺点:单条样本训练量大。样本过少,则无法对所有样本预测得到好的效果。

我们对 Pointwise 和 Listwise 都做了实验,最终我们的系统采用了 Listwise 的方案。主要原因是在我们的标注方式下,Listwise 的方案更容易标注。具体实现上我们采用了 LightGBM 的框架。

评估

我们使用了 NDCG,AUC 和验证点击率的方式对模型进行评估。

  • NDCG,归一化折损累计增益。NDCG 是推荐和搜索中比较常用的评估方法,用来整体评估排序结果的准确性。

  • AUC,AUC 主要反映排序能力的相对性,用于在正负样本不均衡的情况衡量离线模型拟合情况。

  • 重放有点击历史数据的点击率,使用待评估的模型预测有点击的历史输入,排序后得到 Top3, Top5, Top10 点击率作为参考。这种方式比较直观,缺点是不能反映出在无点击历史数据上的效果。

衡量指标

搜索服务变更或新模型上线后,我们需要对线上搜索的真实效果进行衡量。目前我们主要通过搜索的点击率和 Top3 点击率来衡量。由于 Data Catalog 搜索的特殊性,我们更看重模糊搜索的总体点击率和 Top3 点击率(输入和资产名称完全一致的为精确搜索,其它为模糊搜索)。

实际上,点击率并非越高越好,过高的点击率可能意味着:

  • 搜索结果页透出的信息过少,用户不得不点击结果进入资产详情,即使只想查看一些简单的信息。

  • 用户在系统上探索的兴趣较小,只搜熟悉的资产或者确定能搜到的输入。

当然过低的点击率意味着较差的搜索体验。因此,点击率保持在一定健康的区间后,我们也需要关注模糊搜索和精确搜索的占比等指标。

其它模式

除了个性化的搜索需求,也会有一些场景,用户不需要精细化的排序,只需要把包含相关文本的资产都列举出来,因此我们也支持单纯的列表模式,用户可以在列表模式通过指定字段来对搜索结果进行排序。我们也在规划实现一些 query syntax 的功能,以此来支持用户在列表模式下更灵活地约束输入。

后续工作

火山引擎 DataLeap 中的 Data Catalog 系统搜索功能还有很多有意义的工作值得继续探索,例如:

  • 血缘中的搜索。当一个资产的一级下游就超过上千个时,想从当前资产的众多下游中查找到相关的资产并不容易,因此提供基于血缘的筛选和搜索是一个不错的选择。

  • 多租户之间模型的迁移。作为支持多租户的公有云服务,由于租户之间数据的差异,新租户的冷启动问题,以较小的数据量和成本来支持不同租户都有好的搜索体验,也是一个值得挑战的方向。

关于我们

火山引擎大数据研发治理套件 DataLeap

一站式数据中台套件,帮助用户快速完成数据集成、开发、运维、治理、资产、安全等全套数据中台建设,帮助数据团队有效的降低工作成本和数据维护成本、挖掘数据价值、为企业决策提供数据支撑。

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

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

相关文章

Spring Boot + WebSocket 实时监控异常

本文已经收录到Github仓库&#xff0c;该仓库包含计算机基础、Java基础、多线程、JVM、数据库、Redis、Spring、Mybatis、SpringMVC、SpringBoot、分布式、微服务、设计模式、架构、校招社招分享等核心知识点&#xff0c;欢迎star~ Github地址&#xff1a;https://github.com/…

【笔记】容器基础-隔离与限制

Docker 项目的核心原理&#xff1a;为待创建的用户进程 1.启用 Linux Namespace 配置&#xff1a;修改进程视图 2.设置指定的 Cgroups 参数&#xff1a;为进程设置资源限制 3.切换进程的根目录&#xff08;Change Root&#xff09;&#xff1a; 容器的隔离与限制 1.启用 Linux…

MySQL性能优化四 MySQL索引优化实战一

一 查询案例 示例表 CREATE TABLE employees (id int(11) NOT NULL AUTO_INCREMENT,name varchar(24) NOT NULL DEFAULT COMMENT 姓名,age int(11) NOT NULL DEFAULT 0 COMMENT 年龄,position varchar(20) NOT NULL DEFAULT COMMENT 职位,hire_time timestamp NOT NULL DEF…

王凤英,能治好何小鹏的技术“自恋”吗?

1月30日&#xff0c;小鹏官宣一手打造长城汽车(601633)SUV战略转型的前二号人物——王凤英&#xff0c;加盟小鹏出任CEO一职。 虽然这则消息已风传多日&#xff0c;但正式公布的一刻还是在汽车圈内炸开了锅&#xff0c;主要原因有两点&#xff1a;一是王凤英刚刚加入小鹏就被委…

2-1JVM内存分析

一、java类的生命周期 1.加载(把class文件的数据加载到jvm内存的元空间) 2.连接验证 验证语法是否正确准备 给静态变量做内存分配和默认值分配识别 解析常量池 3.初始化静态变量赋初始值静态代码块执行 4.使用(被jvm使用) 5.卸载(如果在程序中没有再使用到这个类,这个类会被从…

跳槽前恶补面试题,成功上岸华为,拿到33k的测开offer

不知不觉间&#xff0c;时间过得真快啊。作为一名程序员&#xff0c;应该都清楚每年的3、4月份和9、10月份都是跳槽的黄金季&#xff0c;各大企业在这段时间会大量招聘人才。在这段时间里&#xff0c;有人欢喜有人悲。想必各位在跳槽前都会做好充足的准备&#xff0c;同样做足了…

还是你厉害啊,用 Python 下载高清视频真速度

今天我们来进行 Python 爬虫实战&#xff0c;学以致用嘛&#xff0c;这也是咱们不断学习的动力&#xff01; 我们要爬取的网站是YY直播&#xff0c;不知道有多少朋友知道&#xff0c;反正小编以前是不知道的&#xff0c;真的不知道~ 那么为什么我们选择这个网站呢&#xff0…

【5.1】Nacos注册中心--认识和安装Nacos/快速入门

【5.1】Nacos注册中心--认识和安装Nacos/快速入门1 认识Nacos2 安装Nacos3 服务注册到Nacos4 总结1 认识Nacos Nacos是阿里巴巴的产品&#xff0c;现在是SpringCloud中的一个组件。相比Eureka功能更加丰富&#xff0c;在国内受欢迎程度较高。 2 安装Nacos 建议大家下载Typora之…

Grafana 系列文章(五):Grafana Explore 查询管理

&#x1f449;️URL: https://grafana.com/docs/grafana/latest/explore/query-management/ &#x1f4dd;Description: Explore 中的查询管理 为了帮助调试查询&#xff0c;Explore 允许你调查查询请求和响应&#xff0c;以及查询统计数据&#xff0c;... Explore 中的查询管理…

CTFshow_萌新--密码篇

一、萌新认证进群大喊萌新码&#xff0c;即可获得。。。。。二、萌新密码1密文&#xff1a;53316C6B5A6A42684D3256695A44566A4E47526A4D5459774C5556375A6D49324D32566C4D4449354F4749345A6A526B4F48303D并给上了一下工具包。①密文首先Hex解码得到串&#xff1a;S1lkZjBhM2Vi…

项目管理工具——Maven

目录儿一、Maven简介二、下载与安装环境配置三、Maven基础概念3.1 仓库3.2 坐标在中央仓库网获取依赖坐标3.3 本地仓库配置3.4 远程仓库配置一、Maven简介 Maven是用java语言编写的。Maven的本质是一个项目管理工具&#xff0c;将项目开发和管理过程抽象成一个项目对象模型(PO…

商城项目的表设计

零、前言 1、优惠卷设计 电商项目中的优惠券系统这样设计&#xff0c;同事直呼 666 &#xff01; 2、SPU和SKU的定义及他们之间的关系 SPU全称Standard Product Unit&#xff0c;即标准化产品单元。 简单理解就是某一种产品。 SKU全称Stock Keeping Unit&#xff0c;即库存量…

PHP多进程(三) 理解多进程

本篇是一个过渡篇 ( 重在理解多进程 以及进程执行过程和进程执行后的数据 ) 废话不多说直接上代码 运行下面代码前 可以先想想有几个进程以及$count 是多少? <?php// 开始多进程 $count 10; for ($i0;$i<2;$i){epd(我是循环记数值.$i);$pid pcntl_fork(); // fork…

使用DBeaver 编辑链接达梦数据库

1、点击 “数据库”&#xff0c;选择“驱动管理器” 2、选择“新建” 3、 设置驱动 驱动名称&#xff1a;自定义 这里命名为“DM” 类名&#xff1a; dm.jdbc.driver.DmDriver URL模板&#xff1a;jdbc:dm://{host}:{port} 或jdbc:dm://{host}[:{port}]/[{database}] 默认端…

根据java反射-手写springIoC

我们都知道&#xff0c;Spring框架的IOC是基于Java反射机制实现的&#xff0c;下面我们先回顾一下java反射。 回顾Java反射 Java反射机制是在运行状态中&#xff0c;对于任意一个类&#xff0c;都能够知道这个类的所有属性和方法&#xff1b;对于任意一个对象&#xff0c;都能…

ResNet简单介绍+Pytroch代码实现

文章目录一、背景介绍二、ResNet网络结构1.ResNet34结构示意图2.不同层数的ResNet采用的Block结构。3.不同层数的ResNet网络结构示意图4.实验结果三、Pytroch代码1.代码简单介绍2. 常见ResNet网络代码汇总四、参考文献一、背景介绍 问题&#xff1a; 当网络层数越来越深时&…

Vulkan 编程指南记录

1 创建Vulkan instance 利用CreateInfo结构体指定硬件驱动需要使用的程序信息&#xff0c;这些信息可能会被作为驱动程序的优化依据指定程序需要使用的全局扩展。比如和窗口系统交互的扩展&#xff08;通过glfw库的接口获取&#xff09;。可以通过vkEnumerateInstanceExtensio…

一篇文章全知全能SpringBoot Bean的生命周期

系列文章&#xff1a;https://gamwatcher.blog.csdn.net/article/details/124603278这篇文章也是计划了蛮久的了&#xff0c;一直没写&#xff0c;正所谓大道行思&#xff0c;取则行远&#xff0c;总结也是学习的一种方式。&#x1f648;记得看目录哦1、关于spring1.1 什么是sp…

Spring Security在前端后端分离项目中的使用

Spring Security 是 Spring 家族中的一个安全管理框架&#xff0c;可以和Spring Boot项目很方便的集成。Spring Security框架的两大核心功能&#xff1a;认证和授权 认证&#xff1a; 验证当前访问系统的是不是本系统的用户&#xff0c;并且要确认具体是哪个用户。简单的理解就…