同程旅行 全栈 春招 凉经 一面 SK精选
KeyWords
同程旅行 - 全栈开发 - 长沙 - Java - 官网 - 25届 - 科班 - 春招 - 凉经
Collection
Withstand Op.K No.I
Locate
长沙
Platform
官网 / 波斯直ping
Status
完咯, 肯定没
时间线
- 3月初 投递
- 3.22 一面
流程
一面
46min
- 你身上会的技能? 不限制方面说一两个最好的?
- 项目管理架构拆分, 还有发散能力, 好. 那你项目搭的有多好? 或者你怎么做好这件事, 你说下
- 好, 我讲一个简单的场景, 你给我把系统搭建出来, 描述: 你需要开发一个接口, 这个接口有接收东西和输出东西的功能, 内部的处理就是一些数据刷洗? 不不, 不是整体业务逻辑. 我要你把软件包结构描述一下?
- (JUC) 换JUC的题, 有一个 实现计数器, 你有几种方法 (多线程场景)
- (原理 + 实现) 拷打 CAS + 实际运用
- 2 * 8 = 多少, 在 Java里面怎么算? 最快性能的是那个? CPU和内存都没有其他限制, 2和8就是阿拉伯数字不是别的类 (我确认了)
- 那么两个很大的数相乘, 你怎么办? Integer和Long的限制都超过了, 你的办法是什么?
- 中间件会哪些? Redis你用过哪些数据类型? GEO, HyperLogLog... 那好 GEO 的位置怎么计算的呢? 联系业务说一下
- 偶吼吼, 经纬度业务是吧, 那我问你, 那我问你: 你不搁河百么, 你到湖南这地球上两点间的距离怎么计算?
- 回到中间件, 拷打 MQ 的场景. (问简单场景)
- 打断上述, 问 MQ 使用的那些模式? 介绍下 (模式) (问基础)
- 场景: 我有一个消费者只能处理一个类型的订单, 有另一个消费者能处理两个类型的订单, 请把交换机和队列的对应关系描述出来 (问场景八股)
- MQ交换机的作用? (大概问是底层原理吧, 控制水温直接给我一拳打死, 下面就是垃圾时间咯)
- 爬虫你的理解? 你之前做过吗? 你是咋做爬虫的? 用什么开发的?
- 场景: 你需要使用爬虫去爬取一个网站的信息, 需要怎么保证你的登陆状态? 说下你的理解和思路
- 对爬虫感兴趣吗
- 后端 GO 用过吗? 其他技术栈啥的...
- (人事题) 你的方案和领导冲突, 人家给你建议, 你怎么想? 你会不会觉得很不爽立刻一板砖丢过去
- 你在干什么, 啥时候过来提前实习?
- BASE地怎么样?
- 反问环节
个人
-
听到之后有点绷不住, 会的技能不是简历里面写了吗, 于是确认到底是什么方面的. 结果又不限制 (就和那个八股送命题一样, 自己也知道完蛋了, 一上来就来这种明显是要往死里打)
先说后端开发, 然后细化点, 选择了 系统架构设计搭建 (感觉自己项目啥的看的多, 自己也做过, 虽然知道大概是要被拷打了, 但还是铁骨铮铮的上了) 这个作为点.
然后就是说自己的项目进行佐证, 什么6k行的课设拉, 什么 DDD + Func + Flow 拉, 什么从0到1拉...
补充点就是可能发散思维比较好, 有想象力之类, 举了下项目和生活的例子
-
主要是说团队协作中, 资源分配, 工作量区块等等 (Oh damn it 我怎么忘记把DDD的设计思路分享下), 需要指出我实习时候差不多一个部门300人的情况下如何去做资源的分治这些问题. 然后回到自己能负责的这些点, 再描绘下自己从一开始接触 0-1 开发 -> 后面的吸收经验的更新的方案 (自己的操作系统模拟项目拉扯半天, 强调用原生Java而不使用框架去做的挑战性), 还有就是最近做的HashMap重写, 要自己把源码扒下来完全重写一遍, 硬活.
-
一开始没整明白, 先叽里呱啦扯了一大堆具体的业务逻辑业务点. 后面补充说要我直接人肉思考包结构我才明白了, 直接红温!!!
概念方面确实是太抽象了, 因此我只能先给自己架设些简单的场景, 比如抽象到具体的架构设计, 使用各种设计模式, 稍微说了两个, 然后说对应一小个区域我要采用什么样的包结构分治... 但是总体的大的思路还是没有一个整体的思维, 没能连接起来. 原因应该是自己经验不足, 再加上直接想的话我的额皮质内存不足了... DDD和微服务也没讲到点, 完蛋咯我都不敢听 (我只能尬笑, 最后红温小丑, 面试官也难绷 (给台阶下了, 感谢))
-
CAS思路 和 加锁思路, 具体的代码没回答卖个关子等他问我 (结果没问), 贴一个我的笔记
volatile int 的局限性:
-
volatile
关键字只能保证变量的可见性,但无法保证操作的原子性。例如counter++
操作并非原子操作,多线程并发环境下会导致竞争问题。
高并发计数器设计:
- AtomicInteger/AtomicLong: 利用CAS(Compare-And-Swap)操作实现无锁自增,保证原子性。
- LongAdder/LongAccumulator: 在极高并发场景下,使用分段计数减少竞争热点,性能优于单个Atomic类。
- 锁机制: 也可采用加锁策略,但在高并发下可能会带来额外开销。
-
-
叽里呱啦, 最后扯到自己的项目里面的数据库CAS, 介绍场景和实际运用 (我真不想把战线僵持在那些背的底层原理, 还是推出去, 让人多拷打些项目场景我比较舒服)
-
总不能答"小学生都会", 这我大呼不妙, 这是要把我往死里整的节奏了. 于是我直接把底层 2 * 8 用二进制计算那个说了, 直接说 我用 << 1 左移一位进行计算, 这种计算更贴近机器实操, 应该是更快的 (我也想不起来为什么哪个快, 以前有看过但是忘记了 ... 瞎扯淡). 我说了下左移的操作方法, 但是感觉确实没答到点上. 于是回去整理了下也拓展了不是常量的 2的幂 乘法:
如果这两个数字都是字面量(即常量),编译器会在编译期进行常量折叠,直接把计算结果 16 替换到字节码中,所以运行时根本就不会执行乘法运算,这也是最快最好的方式
但是如果这两个数字有一个是变量, 那就麻烦了.
底层计算过程概述
-
常量折叠(Compile-time optimization):
- 对于
2 * 8
,由于操作数都是常量,Java 编译器直接计算出 16,并在编译后的字节码中把该表达式替换为常量 16。这样在运行时,虚拟机栈中只需要把数字 16 压栈,而不需要执行乘法指令。
- 对于
-
乘法操作(imul 指令):
-
如果运算数不是常量(例如变量参与计算),
2 * 8
会生成字节码指令imul
。在 JVM 执行时,会先把操作数(例如局部变量或常量)压入操作数栈,然后执行imul
指令:-
imul
指令会从操作数栈中弹出两个 int 值, - 将它们相乘,
- 然后将结果(16)压回栈中。
-
-
-
位移操作(ishl 指令):
-
对于
2 << 3
,编译器生成的是ishl
指令。执行过程如下:- 数字 2 以 int 形式压入操作数栈,
- 然后压入右侧的移位数 3,
-
ishl
指令从栈中弹出这两个值, - 将 2 的二进制表示向左移动 3 位(相当于乘以 2³),
- 结果同样是 16,再压入栈中。
-
- 性能上: 由于常量折叠,写
2 * 8
会在编译期就变成 16,所以运行时没有额外的计算;如果是变量运算,现代 JVM 和 CPU 对于乘以常量(特别是常数 2 的幂)通常会进行优化,有时甚至会将乘法转换成左移操作,所以两者在性能上几乎没有区别。 - 可读性上: 使用乘法运算符
*
更符合直观的数学表达,代码可读性更好,而位移操作符则更适合需要手动优化或底层操作时使用。
也就是说, 实际上我算是歪打正着?
-
-
最先想到是放不下肯定要放下去, 字符串来存储. 联系上面这个位运算我想到说直接进行位运算的拆分, 就是不管他多大, 直接有这个 2的幂来进行 缩放 也是可以存下的, 直接存到String 中进行, 就像我们的科学计数法一样. 然后还说工具类的封装思路.
提醒说, 可以参考人的算术乘法, 就是单个去乘, 最后加起来.
-
想让人问Redis, 我成功了, 但是没想到问我GEO, 这个我是真忘记了, 叽里呱啦业务也没说好, 其实那个是一个缓存的, 计算还是在数据库里计算, 因此我也不会 Redis 里的 GEO命令... 哈哈哈完咯, 贴一个
GEO 常见的命令有:
- GEOADD:添加一个地理空间信息,包含:经度(longitude)、纬度(latitude)、值(member)
- GEODIST:计算指定的两个点之间的距离并返回
- GEOHASH:将指定member的坐标转为hash字符串形式并返回
- GEOPOS:返回指定member的坐标
- GEORADIUS:指定圆心、半径,找到该圆内包含的所有member,并按照与圆心之间的距离排序后返回. 6.以后已废弃
- GEOSEARCH:在指定范围内搜索member,并按照与指定点之间的距离排序后返回. 范围可以是圆形或矩形. 6.2.新功能
- GEOSEARCHSTORE:与GEOSEARCH功能一致,不过可以把结果存储到一个指定的key. 6.2.新功能
-
大概是智力题, 也许是想问我业务, 但是我扯不下去了, 只能说是高中教的球面几何, 我忘干净了... 他反手掰扯了什么球面扇形的计算
-
简单八股介绍.
-
有点忘记了, AMQP 的规约 什么 一个监听器对一个消费队列, 乱七八糟的脑子快速降级(瓦特)忘了, 结果答的稀烂只支支吾吾答出了俩 (直接连, 主题)!!! 下去之后狠狠鞭打了自己 (确实中间件 MQ 和 ELK 没咋被用到, 最近实习中也没接触到就噶了)
在 AMQP 协议中,消息队列(MQ)使用的模式主要有以下几种:
- Direct Exchange:
直接交换机根据消息的路由键将消息发送到绑定到该交换机的队列中。
适用于精确匹配的场景。 - Fanout Exchange:
扇出交换机将消息广播到所有绑定到该交换机的队列中。
适用于广播消息的场景。 - Topic Exchange:
主题交换机根据消息的路由键模式将消息发送到绑定到该交换机的队列中。
适用于模式匹配的场景。 - Headers Exchange:
头交换机根据消息头属性将消息发送到绑定到该交换机的队列中。
适用于基于消息头属性的路由场景。
- Direct Exchange:
直接交换机根据消息的路由键将消息发送到绑定到该交换机的队列中。
-
按照主题进行主题模式, 有一个接受所有的, 有一个接受一个... 感觉没到点上去. 也说了直接绑定的呆呆的模式...
提示说, 别忘了还有 "*" 的这种主题键, 我明明上周见过, 怎么就脑子瓦特了
-
把消息按照一定规则转发出去, 到对应的队列 (概括了一下), 再深的作用就是... (我想不起来原理了, 嗯想, 憋的脸都红了, 面试官忍不住了, 说 要是你不知道就说不知道吧, 没关系的, 因为毕竟你不可能做到面面俱到的, 太温油了, 赞!)
-
之前学校里面有做过项目, 有这个东西. 爬虫这块, 就是调包 (我无语了, 太久的事情了想不起来) 没办法, 只能说让我们学生去为了完成课设去手撕一个轮子确实不切实际
-
联系自己的项目, 说 Jmeter Postman 这种情况, 再说到目标网站是怎么做登陆的 (怎么可能知道人家是怎么写的代码, 因此我说可以去测试, 观察来设计爬虫思路 (不能碰的滑梯)), 比如有的就有反爬虫机制, 有的是限流, 风控IP等等情况, 要具体去分析, 再列几点就差不多了. 有提到一个用户Agent代理去发起请求这个过程...
-
自己最近在做本地AI大模型的训练, 准备学习相关查找资料的内容等等...
-
自己大二时候有一个小挑战, 一个月掌握 Kotlin, Ruby, Java, Python, Go, JavaScript 的基础语法 (我真的去学了, 那几页笔记本日期都是2022年的 (骄傲)), 所以基本语法是了解的, 但是开发的大框架肯定要现学 (没辙). 其他技术栈就简历里那些旮旯
-
我分情况来答, 比如自己十拿九稳的场景, 还有不熟悉的场景, 再联系项目排期等等. 更大的分类是 生活 还是 职场 这种分发. 总之要往团队协作方向去靠就是了
-
(我也看到了有关言论, 不考虑了)
-
水......我喜欢甜的, 长沙很辣, 对我的后门不好 (开玩笑, 怎么可能这么回答)
-
自己独创反问问题1 - 项目迭代相关, 来自实习经历2
-
自己独创反问问题2 - 标品沉淀相关, 来自实习经历1
-
自己独创反问问题3 - 自己的项目没上线就是一文不值是吗? 来自去年的快看漫画二面
回答很搞, 我回味了一晚上
如果是你自发的写些小项目, 我会觉得你这个家伙对技术感兴趣, 有自驱力...
如果是你的大学课设, 毕设啥的, 不是自发的, 我会觉得你很一般: 你连自己的专业都不太感兴趣...
所以我是鼓励你们不管是去提升自己的技术水平也好, 生活水平也罢, 加油吧
在说我吗? 没错 我一个是原创项目, 一个是毕设来的, 一个是课设来的, 可问题是 课设是满分课设, 还二开了两次 + HashMap重写, 是我真的认真去做的了; 毕设也是我全部技术力都压进去的玩意, 绝对不是敷衍的. 但我明显能感觉到话里的意思, 可能真的我自己很一般吧. 我不能说我以为, 我要想到人家怎么想的 (下面这段由于涉及个人隐私, 删了)
结果
(个人)
面试体验超绝无敌螺旋升天的好! 是我目前最好最拷打的一次, 只能说不愧是有知名产品的大公司. 我俩经常互相难绷, 面试间里充满了快活的空气 (太舒服了bro)
原先写的是: "这是最好的一次面试", 但我今天涂掉了. 因为我面的一坨屎. 后面一家面的才算更好, 请继续关注我的下篇文章 (某中小厂, 可能要被某鸽我的厂插队了) !!!
总之是感谢面试机会, 也给了我很多思考点, 这位帅气的面试官必须给他个大大的赞! (最近我的面试里差不多就人家完全开摄像头的, 你品)
但是可能公司相关的风评我也看了, 加上后面的个人安排, 于是也不打算推进后面的流程了
3.31 / 2025, 改
#春招##面经##Java##同程秋招#