文章目录
- 美团一面面经
-
- 面试内容
- 小结
美团一面面经
面试内容
1、自我介绍
2、怼项目(立项缘由,负责模块,项目功能)
3、框架选型(后端 springboot ,ORM 使用 mybatis)
4、项目中的难点(多表查询,使用 xml 实现)
5、使用 xml 的好处(这个我一时还真想不起来)
6、前后端分离项目,是如何部署的(vue 打包成静态资源,使用 nginx 部署 )
7、权限管理是怎么做的(权限表 user user_role role 表)
8、如果要将权限粒度细到按钮,该怎么办(role role_quality 表,将不同角色对应的权限信息存入数据库,每次登录的时候从数据库中查出来)
9、登录超时怎么做(登录之后,将登录信息存入 redis 缓存)
10、redis 超时使用的什么函数(这个没答出来,后来查了一下,直接在设置的时候添加超时时间即可
stringRedisTemplate.opsForValue().set("baike", "100", 60 * 10, TimeUnit.SECONDS);
)
11、锁的实现,你有什么思路(synchronized,Lock,操作之前获取所有资源)
12、synchronized 怎么使用(对象锁,方法使用 synchronized)
13、Lock 怎么使用
14、Lock 的底层实现(Lock -> 管程(java 实现)-> mutex 锁(OS 实现))
15、AQS (没复习到…)
16、线程怎么实现排队
17、消息队列的作用(防止瞬时高并发下的服务器宕机,削峰填谷)
18、消息队列某个请求出错,但是后续还希望再次执行这个请求,怎么办
19、对出错的请求设置一个重试次数,消息队列是怎么实现的
20、HashMap put 的执行流程(hash函数 -> 放入 -> 出现冲突,冲突解决(链表,红黑树)-> 负载因子,扩容)
21、算法
算法面试官给我放了4道,我选了第三和第四题
- 算法题1:数组去重(给一个有序数组,原地去重,使用双指针)
public int removeDuplicates(int[] nums) {
if (nums.length<=1) return nums.length;
int l=1,r=1;
while (r<nums.length) {
if (nums[r]!=nums[r-1]) {
nums[l]=nums[r];
l++;
}
r++;
}
return l;
}
- **算法题2:**找数组所有子集(
的所有子集为[1,2,3]
)[[],[1],[2],[1,2],[3],[1,3],[2,3],[1,2,3]]
回溯题,为了求稳,当时没选
private List<List<Integer>> res = new ArrayList<>();
private List<Integer> track = new ArrayList<>();
public List<List<Integer>> subsets(int[] nums) {
dfs(0,nums);
return res;
}
public void dfs(int index,int[] nums) {
// 递归终止
if (index>=nums.length) {
// 一定要新 new 一个 List
res.add(new ArrayList<>(track));
return;
}
// 当前位置选
track.add(nums[index]);
dfs(index+1,nums);
track.remove(track.size()-1);
// 当前位置不选
dfs(index+1,nums);
}
- **算法题3:**两数之和(一个排好序的数组,找和为 target 的两个数,如果有多个答案,找乘积最小的)
经典双指针题目,不是很难,为了求稳选了它
- **算法题4:**找一组数中缺少的最小的正整数(
答案是[-1,1,3,4]
,2
答案是[2,3,4,5]
)6
这道题我给的思路是构建小根堆,然后依次取根,找到非负非连续的两个数,其中间的数就是我们的答案
我就是把建堆的过程写了,后面的实现说了个思路
其实用排序也可以写,但是复杂度比用堆大
public void buildHeap(int[]arr,int n) {
for (int i = (n/2)-1; i >=0; i--) {
heapify(arr,i,n);
}
}
public void heapify(int[]arr,int i,int n) {
while (i*2+1<n) {
int child = i * 2 + 1;
if (child+1<n && arr[child]>arr[child+1]) child++;
if (arr[child]>=arr[i]) return;
swap(arr,i,child);
i=child;
}
}
public void swap(int[]arr,int x,int y) {
int tmp = arr[x];
arr[x]=arr[y];
arr[y]=tmp;
}
22、你还有什么问题吗?(部门负责的业务,我的表现)
小结
这次面试写算法的时间比较多, OS 计网啥的都没问,花力气准备的 JVM 也没考到
还是那个问题, JUC 那块儿要好好看,现在就属这一块儿还比较薄弱
还有就是有空要看看集合的底层源码