⭐问题归类

实际开发中或者面试中遇到这种场景的问题,一定要抽象出来归类。然后再去解决。

海量数据下的实时模糊检索问题

核心思路是:将“模糊检索”工作从关系型数据库(如MySQL)中剥离,交给专业的搜索/分析引擎来处理。

例如人:通过名字模糊查询用户,2000w数据,20%每月数据量增长,返回列表要怎么做?
方案一:mysql硬撑
方案二:引入第三方专业引擎,如ES,这是处理海量数据模糊搜索的标准工业级方案。
方案三:高阶方案——分库分表 + ES

线程安全问题

下面这段代码有什么线程安全问题,有几种方案解决?

1
2
3
4
5
6
7
8
9
10
public class demo {

public void test(){
ReentrantLock lock = new ReentrantLock();
lock.lock();
//处理业务

lock.unlock();
}
}

问题:

  • 锁是局部变量,无法实现线程间互斥
  • 未使用 try-finally,可能造成锁永不释放

解决方案一:将锁提升为成员变量,并配合使用try-finally

1
2
3
4
5
6
7
8
9
10
11
12
public class Demo {
private final ReentrantLock lock = new ReentrantLock(); // 实例锁

public void test() {
lock.lock();
try {
// 处理业务
} finally {
lock.unlock();
}
}
}

优点:同一个 Demo 实例的所有线程共享一把锁,实现互斥。
缺点:如果多个 Demo 实例,则锁不共享;如需全局共享,用静态变量。

方案二:使用静态所(所有实例共享)

1
2
3
4
5
6
7
8
9
10
11
12
public class Demo {
private static final ReentrantLock lock = new ReentrantLock();

public void test() {
lock.lock();
try {
// 处理业务
} finally {
lock.unlock();
}
}
}

优点:所有实例所有线程共用一把锁,类级别互斥。
缺点:并发度最低,适合保护静态资源。

方案三:使用synchronized内置锁

1
2
3
4
5
public class Demo {
public synchronized void test() { // 实例方法锁,等效于 synchronized(this)
// 处理业务
}
}

或者

1
2
3
4
5
6
7
8
public class Demo {
private final Object lock = new Object();
public void test() {
synchronized(lock) {
// 处理业务
}
}
}

方案四:使用ReentrantLock的静态内部类单例锁

1
2
3
4
5
6
7
8
9
// 静态内部类持有锁实例(单例)
private static class LockHolder {
private static final ReentrantLock LOCK = new ReentrantLock();
}

// 对外提供获取锁的方法(可选)
private static ReentrantLock getLock() {
return LockHolder.LOCK;
}

网络安全性问题

例如:前端和minio直接存数据,会有安全问题。如何解决?

解决这个问题的核心思路是:由可信的后端服务颁发有时效、有限权限的临时凭证,前端仅使用这些凭证与 MinIO 交互。

主要有两种标准的解决方案:预签名 URL (Presigned URL) 和 STS 临时凭证 (Security Token Service)。

  • 预签名:将有时效性的Access Key 和 Secret Key放在url中,minio去验证签名
  • STS临时凭证:给前端颁发一组临时的 Access Key、Secret Key 和 Session Token,前端可以在有效期内和权限范围内自由操作 MinIO。

docker相关问题

编写Dockerfile:这是一个包含构建指令的文本文件,定义了从基础环境、依赖安装、端口映射和启动命令的全部步骤
集群情况下使用:docker buildx bake一次构建多个镜像,提高效率。