编程导航面经话题讨论

面经

983 参与
分享

快来分享你的内容吧~

点击登录,快来和大家讨论吧~
表情
图片
话题
打卡
综合
交流
文章
问答

招商银行外包面试经历

--- ## 面试录音文字整理(26分05秒) ### 开场 **面试官**:方便开一下摄像头吗? **候选人**:摄像头方便。 **面试官**:行,你先做个自我介绍。 --- ### 自我介绍 & 项目介绍 **候选人**:好的,此除省略1000+文字 **面试官**:业务这方面的话,其实这不是核心,因为你的业务跟我们业务完全就是不搭边的。问几个技术问题吧。 --- ### 过滤器 & 拦截器 **面试官**:过滤器和拦截器了解吗? **候选人**:过滤器拦截器,这个了解。过滤器的话,它就是Servlet的过滤器,相当于实现这个Filter接口,当它这个相当于你可以根据它这个Request的一些参数进行判断,也可以调用这个Response对象写一些东西。一般,如果一般过滤器常用的作用就是对这个,一般做对请求做一些拦截,比如说request的一些URI之类的东西,判断一下,如果不合理,相当于就直接response写一个什么无效之类的,直接return,有效的调用filter点doFilterChain。 拦截器的话,它是SpringMVC里面的一个机制,相当于它这个的话,你要实现SpringMVC的HandlerInterceptor接口,它里面提供了三个方法,一个叫preHandle,一个叫postHandle,一个叫afterCompletion。preHandle就是它最终Spring的目标,controller目标方法之前,执行前它会调这个preHandle,如果这个方法你返回了false,它就不会去调用目标方法。 postHandle就是目标方法执行之后,afterCompletion就相当于目标方法执行之后,这个响应写回之后,它会调这个afterCompletion。HandlerInterceptor的话,它最终Spring去调用的时候,它相当于它是在这个DispatcherServlet里面,根据你这个request对象去获取到它这个handler execution chain,相当于他把这个拦截器的链,还有相当于你最终要具体处理的那个handler method一起获取到。 相当于在调用handler method之前,他就会循环去遍历这个handler interceptor的preHandle方法,如果其中有一个失败,他直接请求就结束了,postHandle也不会执行,直接去逆序执行afterCompletion,相当于把执行,比如说执行了5个的preHandle,他再去执行5个的afterCompletion。preHandle是顺序执行,afterCompletion是逆序执行。 **面试官**:那这个顺序可以编排吗? **候选人**:编排,这个顺序是可以编排的,相当于这个编排的话,直接实现这个Spring的Order接口,相当于直接具体给它返回一个顺序,就可以编排。 **面试官**:实际使用场景,你用的什么拦截器?你用拦截器干了啥?做了啥?在你项目组,你不要说广泛的,在你项目组。 **候选人**:在我项目组里面,我用它来防重复提交。相当于HandlerInterceptor里面,它这个的话,它处理的preHandle的时候,相当于可以拿到handler method对象,这handler method对象可以获取到方法上的注解信息。我相当于写了一个通用的注解叫RepeatSubmit,相当于可以定义他这个具体用户,同一个用户在多少秒之内只能提交,这个URI多少次数,相当于我拿到这个他对应的URI和用户ID拼成一个key。 **面试官**:那你这里为什么不用AOP呢? **候选人**:AOP,这个其实,因为用AOP其实可以实现同样作用,用这个handler interceptor主要是当时是为了考虑扩展,因为相当于只根据比如说只根据URI去做是比较简单,后续可能可以直接通过request,那个request body生成MD5值,然后生成key,这样的话就相当于几乎可以做基于请求体的级别的来,相当于基于同一次请求的防重复提交。 然后基于AOP其实也差不多的道理,相当于你针对你的目标方法之前,通过这个去实现一个环绕通知方法,直接写一个@Annotation的表达式,也可以达到同样的效果。当时主要是因为考虑到几种场景,一个是扩展,还有一个是相当于我们内部,比如说定时任务调用是获取不到用户编号,所以说就相当于这样的话就限内部一些定时任务的方法,它是调用这个RepeatSubmit注解是没用的,差不多是这个原因。 --- ### 线程池 **面试官**:你有用过线程池吗? **候选人**:线程池有用过,线程池的话我们这边相当于线程池一般有两种用法嘛。一种就是相当于定时任务去处理一个比较复杂,比较大的任务,耗时任务,相当于把这个耗时任务做一个拆分,拆分成一个个小的任务的一个list,再把这个list,再创建一个CountDownLatch,就是让它的大小等于这个list的大小,相当于初始化一个CountDownLatch的初始化值,再去循环调用那个execute的方法,在每一个任务处理完的finally里面去调这CountDownLatch countDown,再相当于在... **面试官**:execute和submit的区别? **候选人**:execute方法相当于你直接去执行这么一个,是直接放一个Runnable进去,submit方法它其实是可以放一个Future进去,Future是可以具体获取到那个返回值。 **面试官**:那你这里线程池参数怎么配? **候选人**:线程池参数,一般的话就比较简单的场景,就比如说直接给它配线程池参数,一般就是核心线程数,最大线程数,阻塞队列大小。还有拒绝策略,还有他什么线程工厂,还有线程最大存活时间。一般比较最简单的配置方式,就是看CPU核心数,CPU核心数加一作为核心线程数,CPU核心线程数乘二作为最大线程数。 阻塞队列大小的话,根据你具体业务的处理能力。比如说你相当于你的处理效率比较高的话,你最大线程数设的也比较多,你这样就可以把队列设的稍微大一点。拒绝策略的话,根据你具体业务来看,判断你这个任务能不能丢弃。如果说能丢弃,像那种记日志的,就设置成直接忽略那种。相当于有一部分,比如说不能丢弃的,你可能就是直接给他抛异常,或者说直接交由调用者,就相当于调用线程池的线程去执行,或者说你自己去实现。 至于核心线程数和最大线程数,拒绝策略,我这边相当于用到的几种拒绝策略的话,就是两种,一种是我前台写了一个日志拦截器,相当于基于一个filter去记日志。他用户操作了之后,我在这个请求处理之前,就调用线程池,发一条消息到消息队列,把他用户的ID,还有他那个信息发进去,这时候就用Discard的拒绝策略。如果说这个线程的处理能力不够,相当于直接把这个拒绝掉,不要影响到用户正常的前台请求过来。 至于任务执行的时候,我是使用相当于交给调用者,进调用者的线程来处理。因为我这种情况下不是不能丢任务,如果丢任务的话,可能会导致后面出脏数据等一系列问题。所以说当线程池处理能力不够的时候,调用者线程来处理,一般线程池就是。 **面试官**:那他会阻塞吗?他会阻塞后面的任务吗? **候选人**:他会阻塞,相当于他执行不完的时候,他就没办法再往里再添加新的任务了,所以这种一般。 **面试官**:为什么你要用这个策略呢? **候选人**:这种因为一般我们处理涉及到线程池的主要都是后台的定时任务,这种的话相当于定时任务多执行一会也没关系,就是线程池主要是提速的。像针对这个场景,就是针对你这个调用方线程,他也对于这个,就是他吞吐量有比较高要求的这种,我觉得可以就是自己实现一个拒绝策略。比如说你把这个任务记到表里面,或者说发到MQ,表里的话就交给定时任务,他去扫描去补偿,MQ的话就交给消费者去处理。 --- ### 定时任务 & 分布式锁 **面试官**:那定时任务你用了什么?用了哪个? **候选人**:定时任务的话,就是定时分布式任务调度框架嘛。 **面试官**:对,用的哪个框架? **候选人**:分布式任务调度框架,其实这是一个公司自研的分布式调度框架。我们这边只需要配置它调度服务器的服务端的地址,在它像页面上面配置一些,比如说任务执行的Cron表达式,还有它需要方法需要的参数,相当于它就可以具体去执行。 **面试官**:那你知道它其中一些设计的原理吗?比如说我多实例怎么保证它的幂等性? **候选人**:幂等性,这个我有看过它框架的一些源码。它其实幂等性就有点类似于用Redis分布式锁的机制,相当于它任务,它在创建一个任务开始执行的时候,它先尝试,把任务相当于设置到Redis hset进去,最终执行完的时候,相当于把Redis上的数据做删除。中间如果它多次启动,它基于Redis,相当于它加Lua脚本的机制,就把多次启动给拦截掉。 这个过程中当然可能避免不了一些脏数据,比如说他执行到一半挂了,相当于执行到一半挂了,他其实基于心跳,他有ZK心跳监测机制,他是能知道这个任务挂了,但是有少数场景,Redis有脏数据,这个时候可以在他那个前台点一下清除任务流水,相当于把这个删除,也可以再起起来。 --- ### 微服务 & ZK分布式锁 **面试官**:那你微服务组件里用过哪些? **候选人**:微服务组件的话,微服务组件用的比较多的是公司的微服务组件。公司它有一套自研的RPC框架,它相当于调用方,它框架它是用ZK来当注册中心,相当于服务方启动起来的时候,它把它相关的一些服务信息,还有它的实例的IP端口信息注册到ZK上面,之后调用方。 **面试官**:你知道ZK为什么能弄分布式锁吗? **候选人**:这个我知道,ZK分布式锁其实是基于它的几个机制,相当于ZK它有一个临时顺序节点。相当于你往ZK里面,你单独建一个lock的目录,多个线程去同时去创建临时顺序节点,其中只有一个线程能创建到最小的节点,创建到最小的节点的值,它就拿到锁。同时临时节点又比较依赖会话的心跳监测,如果它挂了,它相当于锁也会自动释放。 **面试官**:它跟Redis的分布式锁有什么区别? **候选人**:区别,它俩的区别其实,Redis首先它吞吐量比ZK大很多。相当于你高并发的场景,一般推荐用Redis,还有第二个特点,Redis的一致性其实不如ZK。Redis它比如说它的数据同步是一个异步同步,相当于你master挂了之后,还没,数据还没有同步到slave的时候,它相当于这个时候,它slave被选举成新的master,你这个上面其实没有锁的数据,有可能导致两个线程同时获取到锁。 ZK的话,它是相当于你客户端请求过来,它一定要保证它所有的最终写操作,事务操作全部交给master,就是相当于master在同步给所有的子节点成功之后才返回成功,它的一致性比较高,但是吞吐量比较低。业务上就是像这种框架它使用的是ZK,但是实际业务使用还是建议用Redis分布式锁来保证这吞吐量,同时在基于这个,比如说数据库层面,可以针对... --- ### CAP原理 **面试官**:你知道CAP原理吗? **候选人**:知道。 **面试官**:那Redis是基于什么呢?它是CAP的里面哪种模式? **候选人**:Redis它其实是能保证AP,它不能保证强一致性,因为它是异步同步,顶多可以通过这个,比如说设置,比如说设置这个Redis,它保证数据同,至少同步到一个从节点。才返回。 **面试官**:ZooKeeper它是哪种? **候选人**:ZooKeeper它其实保证的是CP,它像,相当于保证的是强一致性,但是它并不能保证高可用。比如说Zookeeper,它master挂了,它这段时间要重新选举新的master。 **面试官**:对,那所以说刚才那回答刚才那个问题,这两个的,它两个的适用场景,你为什么说一定要建议使用Redis呢? **候选人**:使用Redis的话,相当于因为业务上,比如说你这个用系统有很多用户去访问,如果你这个Redis它比较,相当于它如果挂了的话,影响的时间比较长,影响你这个系统的使用。所以说这个时候一般建议使用这个Redis作为分布式锁,相当于它。 **面试官**:那我需要强一致性呢?那我需要强一致性怎么办? **候选人**:强一致性,你需要强一致性的话,就是要看具体需要什么程度,如果说你特别需要强一致性,可能就要用ZK分布式锁。如果说你可以兼容一下,可以考虑配Redis的参数,相当于设置它主节点至少同步到一个从节点之后,才返回给客户端成功。这样的话其实一定程度上一致性也提高了,同时也能保证。 微服务之间的调用。微服务之间的RPC调用的话,我们公司用的它其实是它一个自研的RPC调用。它相当于通过它有一个类似于,它有一个客户端注册调用注册中心的一个组件,去获取到对应的服务的列表。在进行具体调用的时候,它可能要获取从这个列表之中负载均衡,或者说基于负载均衡的选一个地址,去具体去调用,调用完之后。 **面试官**:就是你不是说,那你实际写的时候会考虑哪些啊?用你们那个自研的RPC里面,它有哪些功能呢? **候选人**:它的功能主要就是,比如说相当于你需要调用其他中心的一个接口,相当于直接可以通过它这个组件去,去写它提交中心的编码,还有对应的他们服务的实现的类名,还有方法名直接就可以调用。你需要考虑的。 **面试官**:除了这个调用功能之外,它有额外的哪些功能呢? **候选人**:额外的功能,它支持一个服务的熔断和降级。比如说熔断的话是我们在配置里面会配置,它比如说在10秒之内,调用接口,如果80%都异常的话,就会触发它这个熔断保护,就相当于直接降级,走我们这个默认实现。相当于同时的话,他等到基本上就是这种配置,就是一个熔断降级。 --- ### 线上问题排查 **面试官**:有排查过现在线上的生产问题吗? **候选人**:线上的生产问题,线上生产问题有排查过,比如说我们那边当时,比如说我们这边消息,我们这边要消费订单中心几百万的消息,相当于消费几百万的消息的话,他这个吞吐量如果下降的话,我们消息就会积压,这个时候就要去排查它消息积压的原因。我们我们这边其实设计的时候就有考虑过这种情况,相当于针对每一个工单的每一个明细,记录它处理的开始时间和结束时间,相当于我们具体去排它每一个,相当于排那些比较慢的规则,相当于把这个规则的SQL拉出来,然后再去排这个SQL的。 **面试官**:为什么会积压呢? **候选人**:为什么会积压?因为它比较依赖消息,比较依赖你客户端的ACK机制嘛,相当于你客户端不ACK,它这个消息队列没办法把这个消息给删掉,所以说客户端处理能力比较慢,就不ACK,它这个积累的越来越多就积压,所以说这时候。 **面试官**:为什么你们那里消费的时候会处理的比较慢呢?它的根本原因是什么? **候选人**:处理的比较慢,其实根本原因是业务逻辑比较慢,根本原因可以从几个方面去分析,一是你这个代码里面有没有去调比较慢的接口,二是你这个SQL里面有没有慢SQL,相当于没走索引的SQL。或者说走了临时表或者filesort的这种SQL。三的话就是,比如说你这个代码逻辑本身就有一些问题,可能有一些死锁之类的,导致它比较慢。就是目前是这几种常见的原因。 **面试官**:那你遇到过OOM的问题吗? **候选人**:OOM的问题的话,这个基本上线上实际遇到的,实际也有遇到OOM的问题,就比如说之前用定时任务去处理大批量任务的时候,去处理大批量数据的时候,有出现OOM。后来其实我们也是,相当于也是判断是程序设计的不合理,相当于针对这个OOM,比如说可能我们就是不要去同时加载太多的对象,比如说加载,比如说可能分布去处理,相当于处理完这一批提交事务再处理下一批,相当于不要同时处理这么一批,相当于把业务上去改造,来减少同时在堆内存里面堆积太多的对象,长期使用对象。 一般前台相关的话,其实OOM相对来说少一点,主要是后端处理大批量数据的时候会有OOM。前台除非说代码里写的哪里有问题,比如说你把一些对象,一些长期使用的对象,给它放到static里面,相当于这种垃圾回收器没办法回收,这种才会导致,或者说你代码里面去调用一些,比如说一些IO流的操作,没去释放,导致内存泄漏。 正常情况下,其实前台相关的,因为我们系统QPS没有那么高。相当于平时平时的情况下,基本上就大约两三千左右,到月底峰值相当于营业员赶业务,也只能达到四五千。除非是定时任务这种消息消费者这种,要处理很多订单中心的数据,或者定时任务这种出现问题。 --- ### 收尾 **面试官**:嗯,我这边就没什么其他问题了,看你有什么想问的。 **候选人**:我们公司它使用的是什么技术栈? **面试官**:Spring Cloud那一套嘛。 **候选人**:哦,Spring Cloud Alibaba这一套。 **面试官**:对。 **候选人**:嗯,好的,那我这边也没什么问题,然后我们这个QPS大约有多少? **面试官**:我们这是主要做数据处理的。 **候选人**:哦,也是类似于我们这种消息消费,相当于数据处理。 **面试官**:你单服务的实例能达到十几个。 **候选人**:嗯,好的,我明白,那我这边没有什么问题了,面试官。 **面试官**:嗯,好。那今天就先这样,后面有结果他们会通知你的。 **候选人**:嗯,好的好的,谢谢。

8月5日小红书1小时拷打(附部分简历)

> **职位**:Product Engineer-产品工程师(AI与全栈方向)-社区工程 ## AI项目 1. Transformer底层原理是什么 2. 详细说一下注意力机制 3. 简单梳理一下你的多Agent是怎么实现的 4. 你这个多Agent上下文是怎么传递的 5. 这个意图识别端到端的转化率是怎么算出来的,之前为什么会失败,现在的优化思路是什么 6. 当你Agent上下文过长时,你是怎么考虑的 7. 你Agent中是用到了多线程处理,那么Python的多线程在真实情况下是会遇到问题的,你有没有考虑到 ## Qoder开源 1. 详细介绍一下你简历上这个开源项目,怎么设计的,当时是怎么理解的 2. 说一下herness的基本思想 ## AI设计 1. 如何设计一个Agent,要求能将需求理解、代码编写、测试、review等串联起来 2. 你说你想通过skill的方式,那么这种固定流程的长skill如何防止信息的丢失和信息的混乱 ## Java项目 1. 你这个数字中台项目主要业务是做什么的 2. 如果说要让你来用AI来赋能这个项目,你的思路是什么 3. 你说你给一个只读权限的账号让AI接管数据库直接与运营对接,其中你要解决什么问题 4. 这个项目做完后,你的下一步工作是什么 ## 基础知识 1. Java的Hashmap的底层数据结构是什么,1.7和1.8的变化是什么? 2. Redis的数据结构 3. Redis如何解决缓存击穿的问题 ## 手撕代码 > 实现一个计算器,要求能加减乘除、回退、清空、支持括号计算 ## 部分简历 ![image.png](https://pic.code-nav.cn/post_picture/1917113123715145729/89diFZaOZQ0odInE.webp) ![image.png](https://pic.code-nav.cn/post_picture/1917113123715145729/2QKZebnqQY57L5Ly.webp)

某芯片生产相关的智能制造外包面试经历

好的,我来重新整理一份更详细、保留更多口语化细节的版本~ --- ## 面试录音文字整理(24分17秒) ### 开场 **面试官**:行,那我们现在开始呗。你先做个简单的自我介绍,然后重点介绍一下自己的项目经验。尤其是可以讲一讲自己最熟悉的一两个项目,它是什么样子的项目和业务,逻辑大概是什么样子的?以及你在项目中负责哪部分?然后自己的一些贡献。之后我们再聊一下用到的哪些技术。 --- ### 自我介绍 & 项目介绍 **候选人**:嗯,好的......此除省略1900字自我介绍 --- ### 全流程参与度 **面试官**:我看你简历里面有写,有全程参与了从需求到设计开发测试以及上线。整个流程的那端都有参与吗? **候选人**:对,开发这边就是,比如说像抽样这个需求。可能我们这边跟组长需要敲定,比如说组长那边可能业务侧的要求就是要抽多少多少订单,我们讨论,比如说业务侧他可能抽取订单的条数经常变化,我们给他做一个灵活配置化的功能,相当于做这种,这样的话用户业务侧想要修改他们这个抽取需求的时候,就改前台的配置页面。我们又讨论,在具体实施的时候又讨论发现分片多进程之后,存在数量不准的问题,之后讨论用Redis来中间做一个分布式计数,来保证最最后的数量是相当于与他们要抽取的数量没有太大差异。 **面试官**:所以你说的讨论是你们team的所有人一起参与这部分的分析讨论。 **候选人**:讨论的话,需求分析阶段是跟组长一起,跟业务侧市场部拉会,相当于跟提出需求方,讨论需求。设计阶段,相当于编写设计文档,在设计评审里面跟组长具体再根据设计文档再讨论。讨论有没有需要填充的地方,最后代码开发阶段,相当于就执行代码开发,之后再进行单元测试,提测,最后在上线的时候可能要把这些脚本准备好,然后把对应的代码分支合并到生产分支执行构建发布,然后到生产才能跟测试一起,走这个过程,如果有问题可能要拉一起分析。 **面试官**:那其中哪些环节是你主导的人员?或者独立完成的? **候选人**:独立完成,这个其实设计阶段,还有开发阶段,还有单元测试,这三个阶段是我独立完成。需求分析是我跟组长一起,相当于一起,跟业务侧那边去拉重新会议讨论。上线阶段的话就是测试那边负责发布,由发布组负责发布,测试负责测试,我负责在旁边监控吧,跟踪一下,跟测试如果有问题,测试把日志发出来,我去分析日志,找原因。 --- ### 需求分析 & 设计经验 **面试官**:嗯,行,你觉得跟业务去做需求分析以及方案设计的这些这两个阶段,需要注意一些什么点呢? **候选人**:需求分析阶段,需求分析阶段的话,主要就是要确定需求,客户业务侧提出的需求合不合理,比如说能不能实现,或者主要是合不合理。比如说他提出来要把一些值写死之类的,这些像这种代码里面写死这种过多的因素肯定是不行的,要搞那种灵活配置化,相当于让他提一次需求,尽量把问题都给解决了,就是不要反复提需求。 设计阶段的话,这个我就比较了解的多一点,因为主要我就负责很多设计,就相当于把过程中的一些表结构基本上都设计出来,表结构表名涉及的数据库要不要分库分表,用什么字段分库分表,大概的数据量估算一下,具体的状态流转级,状态级流转设计出来,把相关的需要多少个定时任务,每个定时任务的参数如何配置梳理出来,再梳理出来前端的一些,比如说一些核心的接口的逻辑也梳理出来,相当于最后再把一些相关的,比如说异常处理的办法,比如说这个进程,如果哪一天出了异常,我们怎么去分析日志,怎么去排查,把这些都给定死,然后再进行讨论,这是需求跟设计阶段。 --- ### 业务复杂度 & 性能优化 **面试官**:你觉得你们的业务复不复杂? **候选人**:业务不复杂,业务的话,业务的话根据具体的跟需求来看吧,有一些需求,就比如说有一些需求是比较简单,业务相对简单,比较复杂的业务就像,像这种,客户资料类,要查询客户资料,查询一些认证相关的表,判断这个用户是什么代办、经办之类的,来获取不同的信息。他细化的东西很复杂,但是针对这种复杂的需求,我觉得可以先尝试,把这个主流程给开发出来,针对细化的东西再慢慢去迭代优化,相当于这样的话,就可以把复杂的业务流程,就是一步步做出来。 **面试官**:行,你们的业务量有多大?业务量。系统的。系统负载有人做了吗? **候选人**:系统负载的话,我们这边相当于,其实相对来说,前台发起的QPS不是很多,大概平时也就只有两三千左右,月底业务人员赶业务的时候,可能可以达到四五千。我们这边消息队列的话,一天差不多是处理百万级别的消息量。针对百万级别的消息量,我们可能把这个消息,再相当于具体一个消息可能匹配多个规则,再分发多个工单,可能数据一天的数据量可以达到千万级别。 **面试官**:那对于这种数据量大,或者性能需求会要比较高的,那你有没有一些实践经验,或者是一些方案设计的方法? **候选人**:这个是,就比如说我们这个消息消费,比我们一天要消费几百万条消息,如果在消费者里面相当于太多的查询,查询这个规则还是一些反复的查询操作。这一步如果要是每一次都查表,它这个就其实很影响性能。如果不查,相当于这一步一定要设计Redis缓存,所有的规则统一走Redis缓存去获取,可以基于生效版本的机制,相当于保证这个查询Redis缓存可以获取到当前生效版本的数据,保证它这个查询缓存就能保证这个数据一致性,跳过所有的查数据库表的获取规则的步骤。这一步从规则方面来降低,还有就是相当于合理的使用线程池吧,相当于有一些可以并发执行的任务,可以用ThreadPoolExecutor加CountDownLatch去做。 还有的一些,比如说数据库的话,前台一般免不了一些数据库查询,虽然一部分的查询可以用Redis缓存几分钟,相当于来减少频繁查库,但是查库是不可避免,所以说一定要设计分库分表。相当于我们这边,它处理多个地市的数据,所以我们可以按照业务,也可以按照地市,相当于做数据库做表的那个水平拆分,拆分多张表。针对于用户,比如说像推送工单,基本上一个人他按月去查也可以,相当于再按照月份再进行水平分表,每一个月每个地市查一张表做分表,同时再合理的添加数据库索引,相当于用户,我们这个派单最好是精确到派给指定的人,这样的话可以根据他这个用户ID加索引,这样优化查询。相当于总共大概就是这几个,一是并发,二是分表,三是加缓存,实在不行就扩资源,大概这几个步骤去处理。 --- ### Redis 数据类型 **面试官**:嗯,你刚才说到了Redis缓存嘛,也就是其实项目中有使用过Redis。 **候选人**:对。 **面试官**:Redis,那就说一下Redis常见的数据类型。 **候选人**:常见的数据类型一般就是它的字符串类型,直接set进去,一般就是set key1 v1,这种就是字符串,然后字符串的话,它可以比较常用的基本就是set、setNX、setEX。还有比如说increase by,decrease by。还有就是list,list也是常用的类型,一般基于查询条件比较少的列表,可以直接基于list缓存到Redis上面,查询的时候可以直接用这个range,去根据用户的分页条件,直接从Redis的list里面返回。 还有就是用哈希,哈希的话,一般规则配置信息我们都会用哈希去存,相当于某一个,针对某一个配置表,我们就会用一个哈希去存,它这里面某个哈希对应的值,是这个规则小的这个JSON的值。还有就是,bitmap位图。Bitmap位图,这个我们主要用的就是相当于布隆过滤器有时候会用的。就是说针对某一个key,计算它几种计算几次哈希值,然后把这几次哈希值都对这个位图的大小去按位与,塞进去。在下一个值,下一次请求到来的时候,再计算哈希值,看那位图上面有没有,如果有的话就相当于这个才是有效数据,如果没有直接给过滤掉,用一个布隆过滤器。还有就是zset,zset的话可以,这zset可以记录一个score得分,还有它的具体的元素的一个值,它可以支持根据分数去排序,然后取前几名,也可以支持批量去获取到某一个区间内的全部元素,删除某一个区间内的全部元素的。 --- ### 设计模式 **面试官**:嗯嗯,你刚才说到了策略模式。那其实是属于加了设计模式中的一种嘛。那你可以再列举几个你熟悉的那种设计模式,以及它们大概是怎么去实现的? **候选人**:OK,它还有常见比较常见的,跟策略模式很像,是模板方法模式。比如说我们系统要做一个文件上传,用户可以根据URL上传,也可以根据直接上传具体的文件。但是上传具体步骤就不是很像,都是处理字节流,然后字节流上传对应的调用方法,上传对应的服务器。基本上可以把字节流上传,还有调用接口这些逻辑,拆写到abstract的template里,相当于具体的URL上传和文件上传,它只需要继承这个类,把具体的URL解析成byte数组,还有byte流和文件解析成byte流的方法实现一下,其他都不用动,这就是模板方法模式。 还有就是装饰器模式,Java的IO流就是装饰器模式。比如说它原本的FileInputStream就是只能处理比较简单的文件读写,然后在它外层你有一个BufferedInputStream,BufferedOutputStream,FileOutputStream刚才讲,然后再你有一个BufferedOutputStream,这样你去写的时候,它就会用这个Buffer去缓冲。然后的话还有比较常见的就是我想想策略模式,模板方法,还有就是工厂模式,像Spring的IOC容器,它其实就是工厂模式,相当于它有一个BeanFactory去获取具体的Bean对象的时候,它把复杂的Bean对象的创建逻辑全部封装到BeanFactory里面,我们再去获取对象,只需要用BeanFactory点getBean就可以。 --- ### 多线程 & 线程池 **面试官**:嗯,然后也前面也说到了多线程,那要多线程就必须介绍一下线程池了。就你在你们在项目中就线程池一般是怎么? **候选人**:一般项目中配置,就用那个ThreadPoolExecutor,之后它基本上有几个重要的参数,一个是核心线程,一个是最大线程,还有阻塞队列大小,还有拒绝策略,还有这个线程工厂名字。以及最大线程空闲时间,一般来说我们比如说像我们配置一个线程池的时候,如果是IO密集型,可能就给它设置成CPU核心数加一,最大线程数设置成CPU核心数线程数乘二,但是是比较理想的情况。一般对线程池一定要添加一个工具类动态去设置值,比如说可以监听ZK上面某个节点变化,动态去设置线程池的参数。等到上线之后,先大批量数据压测,压一把,发现这个处理能力不够的时候,相当于调整线程池参数,比如说发现它设置成CPU核心线程数,最大,核心线程数设置成CPU同样的大小不太合适,相当于给它再调两倍,再压一把试一下,发现不行的话,相当于再把这核心线程数再调小一点,再压一把。 还有就是比如说记录日志的时候,我们也会用线程池,但是记录日志这都属于非核心操作,如果使用太多的线程,相当于可能会影响到这服务器性能,一般这个就这个两三个左右,在业务上再压测一下,基本上如果可以的话,就设置很少的线程数。 **面试官**:那你在项目中有使用哪一种这种多线程的方法去做开发? **候选人**:一般我用的比较多的其实就是两种,一种就是直接,比如说我获取到一组,比如说我要一下执行很多条,执行很多任务,我可能把任务拆分成一个个小任务,把这个小任务就是交给这个线程池去处理,每处理完或者抛异常,直接countDownLatch countDown,然后外层要countDown wait,只等待一些时间,等待所有的线程执行完,再去下,走下面一个。还有一种就是比如说记日志,记日志这种就没必要等,相当于直接处理完,直接调Execute的方法给它传进去,直接我这个请求就结束,给客户端响应。这一般是这两种。 --- ### 收尾 **面试官**:行。行,我没其他问题了。嗯,好的。然后因为我们这边是做那种跟芯片生产相关的智能制造的。所以他对这个信息安全啊,他用的比较重,所以一般我们如果到我们这边的话,你在进办公室之前,大部分地方的手机是不允许带进办公室的,是需要放到外面的密码箱的。 **候选人**:嗯,好的。 **面试官**:因为有很多人可能比较介意这种。 **候选人**:这个不介意,接受。 **面试官**:对,另外就是我们的业务会比较复杂。可能是你接触过的所有业务里面最复杂的一种。就这边可能会有点压力。 **候选人**:可以接受。 **面试官**:你是离职的状态吗?还是? **候选人**:目前是在职。 **面试官**:目前是在职,那是为啥是想想要换一个工作? **候选人**:因为相当于我对这个公司的技术栈,还有常用的业务的处理方法都比较熟悉,相当于后面的提升可能就比较有限,人可能就偏向懒散。就是后面不会有很多成长,所以一定要。就类似于走出舒适圈。 **面试官**:嗯,你就想要一些新的挑战。好,了解。行,那我这边没其他问题了,那我们今天先这样。好的,谢谢。 **候选人**:嗯,好的,谢谢。

深圳融聚汇面经-附带入职求助 一、面试经历 1.0 岗位JD介绍 1. 面试岗位:java开发工程师 2. 面试方式:线下面试 3. 面试时常:2h30min 4. 公司简介:金融证券 大数据 1.1 AI编程相关 1. 做一下自我介绍。 2. 你在项目中做过印象最深刻的内容是什么介绍一下。 3. Agent编排是什么样的?如果要求你对你写的每个Agent做一个监控,检查是否完成或者检查异常要怎么做?你们项目中有涉及到这一部分吗? 4. harness了解吗?介绍一下。 5. plan模式是什么?ReAct模式是什么?他们的区别是什么? 6. 你平时如何使用AI进行Coding?有没有遇到过LLM幻觉问题?如何处理? 7. 你在开发过程中觉得AI编程的优缺点是什么? 1.2 Java相关 1. MySQL的默认存储引擎是什么?其他存储引擎有哪些了解吗?介绍一下。 2. MySQL默认的事务隔离级别是什么?介绍下事务隔离级别。 3. 旁路缓存了解吗?介绍一下。 4. 介绍下你们项目中运用到的缓存技术。 1.3 其他 1. 认为Java语言社区氛围如何? 2. 如果让你转Rust语言你可以接受吗? 二、入职求助 1. 个人情况介绍:楼主最近也算是比较活跃在编程导航了,因为被KO了(那很倒霉了)。说回正题,楼主22年毕业于某211大学网络工程专业,之后入职本地一家小公司,主要做crud(懂得都懂),干了两年,觉得没什么前途,在24年7月跳槽到了华为od干了一年左右,结果被调岗到了前端,因为前端使用asp这种祖传项目,外加坚持古法编程,楼主实在太菜不会写,于25年10月裸辞,之后求职了好几个月,26年3月入职了追觅,6月裁员大屠杀,直接6.31日离职了。也算是命途多舛。7月投递简历,大概面了7-8家没什么下文,今天,哦,现在过了12点,已经是昨天线下面试了深圳融聚汇这家公司,当天下了offer,要求我下周三入职,已经接了,但是还在犹豫要不要去。 2. 犹豫的原因: ①. 下offer和入职都非常着急,我非常担心又是一个很坑爹的工作,说实话被坑怕了 ②. 薪资问题,第一家公司是12k,od给了15k,追觅给了16k,这家公司只能薪资平移16k,但是最主要的是绩效占了50%,试用期3个月,试用期打九折,签约为3年,也就是基本工资只有8000,绩效试用期7000,正式为8000,这让我觉得非常离谱,从来没见过这么离谱的绩效占比,另外五险一金也是按8000来算的。这个占比我其他朋友提出要是绩效考核给一个根本无法完成的任务就很悬,另外一个朋友则表示金融证券加班非常严重。 ③. 工作时间是朝九晚六,离家通勤时间大约一小时。(说实话觉得还挺累的) 3. 现状: 面试安排: ①. 下周一有字节跳动-懂车帝的harness工程师面试邀约 ②. 下周二有泰康人寿-java研发工程师面试邀请 ③. 下周三有金仕达-智能体平台研发工程师面试邀请 其他: ①. 手头offer只有这一个 ②. 面试了成都拓达聚思力-高级java开发工程师有致电,但是因为面试原因没有接听(个人感觉是凉面,面的特别基础特别细,面经后续公布) 4. 问题 ①. 有必要先去这家公司干吗?还是继续待业求职?目前的存款够在深圳支撑3-4个月。 ②. 如果试用期离职,会不会被要求赔偿?如果真的试用期离职了,不在简历上写这段经历可以吗? ③. 个人感觉全职求职有时候真的很没动力学习,感觉非常疲惫,加上这几段工作经历都很糟心,有时候真的觉得太想摆烂了。总结来说就是待在家全职求职觉得没有钱,很焦虑,这也导致有时候学不进去,入职骑驴找马又担心工作期间不能及时面试和复习,也担心简历中再次出现这种短期经历。 总结: 最后写在这里,看看大家的意见,再评估一下,也希望各位大佬们给点建议QAQ孩子真是被坑怕了。(ps:之前欠下很多面经,咕了yes哥,明天就写,下次一定(捂脸)

找实习从7月22号开始投,现在也总算是有offer了

我的学历是一个民办本,刚开始投简历的时候就是在5个招聘软件上疯狂海投,前面几天基本上没有一个回应,当时心态真的是块崩了。。。 投出去大概有200简历吧,就收到了第一次面试:江西江铃公司的面试邀请(岗位写的JAVA/AI),当时也是很珍惜这个机会,疯狂的开始准备八股,以及项目上相关的话术。 #### 第一次面试(江西江铃) 开始面试:(会议四个人->和我对接的hr、一个问我AI的、一个问我JAVA的、还有一个估计是领导之类的) 1、自我介绍 负责AI面试官问: 2、我看你两个AI项目用到的是不同的框架,你说说SpringAIAlibaba和Langchin4j的区别? 3、你项目里的那个输入输出护轨是如何实现的? 3、我这里有100份合同,如果是你?你会如何设计多Agent协作? 4、你了解过dify吗?你对于dify的使用程度? 负责问JAVA的: 1、说说你对微服务的理解? 2、你仿12306购票系统有哪些亮点?如何解决超卖问题? 领导问: 1、你读哪个学校? 2、平时在学校参加过什么吗?(这里我说我参加蓝桥杯拿了省二,结果他听成你打篮球拿了省二等奖是吧....) 结束。。。也没有反问环节,就说2-3天出结果。到现在也还没有结果,发微信去问说什么公司放高温假人事部门还没出结果...(ˉ▽ˉ;)... 全程持续了18分钟,也都回答上来了,但现在已经快5天了,还是没有结果,感觉是没戏了 #### 第二次面试(四川一家小公司) 这家公司主要是AICoding方面的 1、自我介绍 2、我看你有2个Agent相关的项目是吧,来你现在打开共享屏幕演示一下(这点我真没想到,因为有个项目就是一个半成品,前端界面都没有) 3、由于第二个项目的问题,说达不到他们公司的要求,但是这个面试官挺好的应该是老板,主动给我说了还有哪些方面需要提升,最后也让我问还有什么其他想问的吗? #### 第三次面试,也算不上面试(江苏一家电气公司) 这家公司是最奇葩的,我先说一下实习待遇:200一天,大小周,8点-17点,考虑到我距离远还有一次性1000块钱的租房补贴;公司主要业务是做自动化机器人,相当于就是流水线上的那些自动化设备 这家公司是我在前程无忧上投的,投了有2天,招聘才点开我简历来看,接着就立马打电话给我: 1、我的简历上岗位写的是应聘JAVA AI后端实习生,然后这个招聘问我,你为啥简历上写JAVA,现在代码不都用AI来写吗?(问到这里我有点奇怪了,咋问我这个问题?)我回答了一些关于Java 非常适合落地精细化 Agent 权限的案例,然后讲解了一下我的项目,就没了。 2、我滔滔不绝说了一大堆后,招聘说我技术没问题,而且表达能力很好,要我加他微信,问我有兴趣去他们公司吗?加上微信之后,我看出来了这人应该是一个领导类似的职位,而且肯定也不懂技术,就电话沟通10分钟不到,直接让我去他们公司,问我什么时候能动身。 3、问了一些大致的问题后,就开始联系人事部门开始发offer了。(找工作有时候看运气是真没错) #### 总结: 这个offer收到之后,面试也多了起来,后续又约到3个线上面试不过待遇都是100-150一天。 提个建议:我大致也是投了500+的简历,前面几百份几乎都是石沉大海,后面我改变了一下策略:招聘人不理我,我就一直给她发消息,说我稳定长期实习,通勤有保证之类的话,后来要简历的人也逐渐多了起来,后面的几个面试机会,算的上是BOSS硬聘要来的😂

今天面了两家公司,面试时间都比较短直接总结到一起了 第一家 1. 自我介绍 2. 公司两个项目开发中,用到 Codex 或 Claude Code 了吗? 3. 具体是用来写什么?用的是最多的哪个? 4. Claude Code 用的是什么模型? 5. 什么时候开始用的?(精确到具体月份) 6. 是官方账号还是中转站? 7. 当时开发一天用多少钱? 8. 平时用到什么 Skill 或 MCP 吗? 9. Claude Code 怎么写前端?怎么用 Claude Code 写后端? 10. Java 项目代码量很大,你怎么解决上下文问题?Claude Code 用了多久? 11. 讲一下你的个人项目,里面的 AI 功能有哪些? 12. 有用到 Agent 或 RAG 吗?Agent 和 RAG 在里面是怎么执行的? 13. 知识库怎么切片?有做优化吗? 14. 为什么会选择往 AI 方向靠? 15. 反问 第二家 1. 自我介绍 2. 你们之前做过临薪通项目,面对多种角色入驻的场景,你在代码上是怎么设计的? 3. 你们这个项目有用工作流吗? 4. 你们这个项目设计模式用得多吗? 5. 涉及多渠道、多来源的数据,代码里怎么写的? 6. 用工企业的注册入口只有一个还是会有多个地址? 7. 你们有多种计费模式(时薪/日薪/月薪/项目制),这种情况会用哪种设计模式实现? 8. 你们有参与线上部署吗? 9. 反问 感觉不是诚心招人,两家都应该都成为备选了

小公司做海外广告业务的 1.自我介绍 2.你讲一下那个 Spring Bean 的生命周期 3.你讲一下事务的失效情况有哪些? 4. 你讲一下那个 Redis 分布式锁,之前有用到过吗? 5. 那 Redis 的缓存击穿有没有用到过? 6. MySQL 的话,如果有慢查询的话,要怎么去排查去解决? 7.MySQL 的分库分表有了解过吗?使用的数据量不是很多,还是什么? 8. 消息队列有用到吗?定时任务框架有用到过吗? 9. 线上环境出现内存泄漏,要怎么排查和解决? 10. 那怎么去找到是哪一个方法导致的内存泄漏? 11. 工作中有没有遇到过内存泄露 / CPU 异常 / 内存异常的问题? 12. 你最常用的 Docker、Linux 命令有用到过吗? 13. Docker 容器主要是解决了什么问题? 14.工作中有接触过支付类的相关业务吗?支付渠道之类的?能讲一下你们支付的一个大概的流程吗? 这家整体表现还算可以看周一能否给答复

深圳鸿航达科技有限公司面经

## 深圳鸿航达科技有限公司面经 ### 一、基础问题 #### Q1:做一个简单的自我介绍。 #### Q2:为什么要从上一家公司离职? #### Q3:团队有多少人? #### Q4:个人博客写了些什么? #### Q5:工作年限?上一家公司的薪资待遇?多久可以到岗。 ### 二、项目提问 #### Q1:你们的项目后端如何与设备交互? #### Q2:为什么使用HTTP,而不是MQ或者MQTT? #### Q3:数据量有多大? #### Q4:项目中有使用过多线程吗?举个例子。 #### Q5:关于虚拟线程介绍一下。 #### Q6:在工作中遇到的最难问题是什么?如何解决的? #### Q7:在项目中使用过哪些锁?介绍一下。 ### 三、八股文提问 #### Q1:MySQL默认事务隔离级别是什么? #### Q2:MVCC是什么? #### Q3:普通索引和主键索引的区别是什么? #### Q4:SELECT * FROM student WHERE age = 1 的执行流程是怎么样的? #### Q5:普通索引能不能直接拿到数据? #### Q6:ReentrantLock的底层原理是什么? #### Q7:线程安全集合有哪些? #### Q8:ConcurrentHashMap的原理是什么? #### Q9:volatile有什么作用?

平安好医生面试面经-附带回答版本

### Q1:介绍下你自己。 A:面试官你好,我是xxx,计算机相关专业本科毕业,毕业后一直在做 Java 后端和AI相关的项目。最近参与过AI语音助手和设备配套的OTA平台,之前做过企业内部的AI知识助手、云图库和电商。其中AI语音助手和AI知识助手,主要是与AI相关的开发,AI语音助手是将RAG、Tool Calling、实时语音链路落实到Spring Boot、MySQL、Redis这些工程组件上,AI知识助手则偏向于RAG和Tool Calling;OTA平台、云图库和电商则主要是传统的Java后端开发。 ### Q2:RAG检索过程是什么样的? A:在我们的开发应用中,会把RAG分为离线建库和在线检索两部分。 1. 离线侧先解析文档,保留Markdown标题层级、表格和产品版本等metadata,再按照语义边界且chunk,生成向量并写入向量索引,同时建立BM25倒排索引。 2. 在线侧先对query做分类或者改写,并且按照产品、版本、权限做过滤,然后并行做向量召回和关键词召回,用RRF合并候选,必要时用Cross-Encoder精排。最后按token预算去做驱虫和context packing,把来源一起交给模型,证据不足就拒绝回答。 ### Q3:打分过程是什么样的? A:Top K并不是打分算法,它知识按照分数排序后的截断。向量召回的原始分数可能是余弦相似度、点积或者L2距离,BM25则根据词频、逆文档频率和文档长度给分。两路分数不能直接相加时,可以按排名用RRF融合,之后Cross-Encoder把query和chunk一起输入,得到更加精细的相关性分数。最终再取Top-N进入上下文。当然不同向量库的score方向和归一化方向不同,不能只看一个阈值。 ### Q4:ReAct的原理是什么? A:ReAct的核心是模型根据当前观察选择下一步动作,工具返回结果后形成新的观察,再决定继续调用工具还是给出最终答案。生产环境中我们一般不会把内部推理原样展示或者记录,更多的是记录工具名、参数摘要、权限决策、结果状态和可审计的决策说明,另外为了避免循环,还需要限制最大步数、总时长和工具集合。 ### Q5:Plan和ReAct的区别是什么? A:ReAct是每得到一次Observation就决定下一步的Action;Plan-and-Executor则是先形成相对完整的计划,再由执行器逐项执行,必要时重新规划。 ### Q6:Agent完整的工作过程是什么样的? A:请求进来先生成traceId,并且绑定用户、租户和会话;随后组装system规则、当前问题、近期历史、RAG证据、可用工具和权限信息。模型如果选择工具,只输出工具名和结构化参数;服务端做schema、权限、范围、敏感操作二次确认和幂等校验,再通过带超时、重试、熔断的执行器调用。工具结果会被标准化为Observation回填,模型决定继续还是结束。最终回复要包含来源或执行结果,整个过程记录prompt/tool版本、耗时、错误码和审计信息。 ### Q7:上下文组装是什么过程? A:上下文组装是每次调用模型前,把本轮需要的输入按优先级放进token budget。通常包含system prompt、当前问题、最近会话、RAG证据、工具描述、工具结果、用户画像和权限信息。安全规则和当前问题不能被裁掉,RAG证据要按照相关性和多样性选择;旧历史先做滑动窗口,再做摘要。需要注意ChatMemory只是这些信息的一个来源,但是不等于上下文本身。 ### Q8:记忆怎么持久化,如何提取? A:这个功能的本质是把对话历史持久化到MySQL中,然后每次请求大模型之前会根据会话ID查询最近的历史消息,再重新放入模型上下文中。最初使用的Spring AI的内存对话记忆,但是这会导致服务重启后数据丢失,所以我们自定义一个ChatMemory实现Spring AI的ChatMemory接口。从数据层来说,是设计了一张chat_messagede表,通过conservationId区分会话,同时保存消息类型、文本内容和metadata。matadata类型是Map,使用MyBatis-Plus的JacksonTypeHandler将其转换为JSON存入MySQL中。再服务层的具体实现上,add方法负责把Spring AI的Message转换为数据库实体写入;get方法会根据会话ID查询最近N条消息,再转换为对应的UserMessage、AssistantMessage等对象;clear方法负责清空指定会话。最后,把这个自定义的chatMemory配置到MessageChatMemoryAdvisor中,每次请求都携带同一个chatId,Advisor就会自动读取并补充上下文,从而实现跨请求、甚至服务重启后的对话记忆。

面经分享

这段时间经历九次面试,通过了6家公司,最后选择了给我日薪最高,离我最近一家公司(宏图物流) 面经在我的博客中,我就不复制过来了 博客地址:http://blog.cognipix.xyz ![image.png](https://pic.code-nav.cn/post_picture/1638948184199864322/K5Sn9n3Ab7FNzmbH.webp)

下载 APP