一、AI模型集成与推理
1. 在Java后端中调用AI大模型有哪些主流方案?各有什么优缺点?
考察点:对AI工程化落地的方案选型能力。
主要有三种方案:
-
原生Java推理框架:如Deep Java Library(DJL),支持PyTorch/TensorFlow/ONNX等多种后端,可直接在JVM内加载模型推理,延迟最低,但生态不如Python丰富。
-
ONNX Runtime:高性能跨平台推理引擎,支持多种框架导出的模型,通用性好,是当前很多团队的主流选择。
-
微服务封装:用Python(FastAPI/Flask)将模型封装成独立服务,Java通过gRPC或RESTful API调用,解耦性好,便于模型独立迭代,但多了网络开销。
2. 如何设计一个高并发的模型推理服务?模型加载和请求处理如何优化?
考察点:AI服务的性能工程能力。
模型加载放在@PostConstruct中,避免每次请求重复加载。推理服务应同时提供同步 和异步 两种API------短任务用同步,长任务(如图生图)用异步+消息队列。推理优化手段包括:Batching (批量推理提升吞吐)、模型量化 (INT8压缩减少显存占用)、结果缓存(高频问题直接返回缓存结果)。
3. 模型推理比较耗时,导致接口响应慢,你有什么优化思路?
考察点:推理延迟的工程应对策略。
-
流式输出(SSE/WebSocket) :大模型生成时逐Token返回,改善首字延迟体验。
-
异步任务处理:提交任务后立即返回任务ID,通过回调或轮询获取结果。
-
模型预热:服务启动时用 dummy 请求预热模型,避免首次调用冷启动延迟。
-
降级与熔断:AI服务超时时返回兜底答案或规则引擎结果,保证核心流程可用。
4. 如何保证线上模型的稳定性?模型热更新和灰度发布怎么做?
考察点:AI服务的运维与发布策略。
模型热更新可采用双缓冲模式 ------新模型加载完成后原子切换引用,过程中旧模型继续服务。灰度发布可通过流量染色 或Feature Flag 实现:部分用户(如内部员工)先使用新模型,逐步放量。关键是要有模型版本管理 和回滚机制,一旦新模型效果下降或出错能快速切回。
5. DJL(Deep Java Library)中的NDArray是什么?使用不当会造成什么问题?
考察点:对Java深度学习框架底层内存管理的理解。
NDArray是DJL中表示多维数组的核心数据结构,类似于NumPy的ndarray,用于模型推理时的张量操作。常见坑 :toByteBuffer()和toFloatArray()等方法若使用不当会造成严重的内存泄漏 ,导致Java进程消耗数十GB内存被系统强制终止。根本原因是NDArray背后持有原生内存(Native Memory) ,JVM的GC无法自动回收,必须显式调用close()或使用try-with-resources管理。
二、RAG与向量检索
6. 什么是RAG(检索增强生成)?它在企业级AI应用中的核心价值是什么?
考察点:对RAG原理与应用场景的理解。
RAG通过"检索先行、生成补全 "的机制,先从知识库中检索相关信息,再将其作为上下文输入大模型生成答案。核心价值在于低成本解决两大痛点 :大模型训练数据滞后(知识无法实时更新)和幻觉问题(模型编造不存在的事实)。相比重新训练或微调模型,RAG的成本要低几个数量级。
7. RAG系统的完整工作流程是怎样的?在Java中如何实现?
考察点:RAG全链路的技术掌握。
完整流程分为离线 和在线两部分:
-
离线(索引构建) :文档解析(PDF/Word/TXT)→ 文本分块(语义分段,避免语义断裂)→ 向量化(Embedding模型)→ 存入向量数据库。
-
在线(检索生成) :用户Query → 向量化 → 向量检索(相似度匹配Top-K)→ 组装Prompt(检索结果+System Prompt)→ 调用大模型生成 → 返回结果附带引用来源。
Java中可使用Spring AI框架,配合Tika做文档解析、Redis/PGVector/Milvus做向量存储。
8. 向量数据库和关系型数据库的本质区别是什么?如何选型?
考察点:对向量检索技术的理解。
关系型数据库存结构化数据 (二维表),查询基于精确匹配 (SQL);向量数据库存高维向量 (Embedding),查询基于近似最近邻搜索(ANN) ,通过余弦相似度等计算语义相近程度。关系型查询时间随数据量线性增长O(n) ,向量数据库通过HNSW、IVF_PQ等索引实现亚线性O(log n) 。
选型参考:
-
Redis:中小规模、高并发,Spring生态无缝集成
-
PGVector:已有PostgreSQL环境,混合存储需求
-
Milvus:大规模(亿级)、高精度检索场景
9. 向量相似度计算有哪些常用算法?各自适用什么场景?
考察点:对向量检索算法的理解。
-
余弦相似度:关注方向而非大小,适合文本Embedding(最常用)
-
内积(点积) :适合归一化后的向量,计算效率高
-
欧氏距离(L2) :关注绝对距离,适合图像特征等场景
在RAG文本检索中,余弦相似度是首选,因为文本语义更关注"方向一致性"而非"绝对数值大小"。
10. 为什么不能对大规模向量做全量精确搜索?ANN索引的核心思想是什么?
考察点:对向量检索性能瓶颈的理解。
全量精确搜索需要计算Query向量与所有库内向量的相似度,时间复杂度O(n),当数据量达到百万、千万级时,延迟不可接受。
ANN(近似最近邻搜索) 的核心思想是牺牲少量精度换取数量级的性能提升 。通过构建索引结构(如HNSW ------层级可导航小世界图、IVF------倒排文件索引)将向量空间划分区域,检索时只搜索最相关的几个区域,而非全量扫描。
三、AI应用工程化
11. 提示词工程(Prompt Engineering)有哪些核心技巧?如何在实际项目中落地?
考察点:对大模型应用调优的实践能力。
核心技巧包括:
-
角色设定:给模型设定系统提示词,明确角色、任务和约束
-
小样本提示(Few-shot) :给模型提供输入输出示例,让其仿照执行,适合需要固定输出格式的场景
-
思维链(Chain-of-Thought) :引导模型"先思考再回答",提升复杂推理任务的准确性
落地时需要持续迭代优化,可通过A/B测试平台对比不同提示词的效果。提示词本质上是"给模型的代码",需要像写代码一样做版本管理和回归测试。
12. 如何消除AI调用中的"幻觉"问题?
考察点:对AI应用质量保障的理解。
-
提示词优化:更明确的角色定位、添加"如果不知道请说不知道"等限制条件
-
RAG系统 :外挂知识库,让模型基于检索到的内容回答,而非依赖自身参数化记忆
-
结果校验:对模型输出做二次验证(如用另一个模型评估答案质量,或规则校验格式/范围)
-
可观测性 :记录模型输入输出,建立准确度监控 和幻觉检测机制
13. AI Agent是什么?Function Calling/Tool Calling在Agent中扮演什么角色?
考察点:对AI Agent架构的理解。
AI Agent 是能够自主决策、调用工具、完成复杂任务的AI系统,相比单纯的对话模型,Agent具备"行动力"。
Function Calling(工具调用) 允许大模型根据用户请求,结构化地调用外部API或工具 (如查天气、订机票、执行代码)。它是Agent连接"大模型大脑"和"外部世界手脚"的关键桥梁。在Java中,可通过Spring AI的@Tool注解将Java方法暴露给模型调用。
14. 在AI应用中,多轮对话的上下文如何管理和存储?
考察点:对话状态管理的工程实践。
核心思路:用Redis 存储会话上下文,以sessionId为Key,存储历史对话记录。需要考虑的问题:
-
上下文窗口限制 :大模型有Token上限,超出时需要截断 (保留最近N轮)或摘要压缩(用模型总结历史)
-
成本控制:每次请求携带全部历史上下文会增加Token消耗,需要权衡上下文完整性和成本
-
持久化:关键会话可同步落库,支持会话恢复和数据分析
15. 如何设计AI服务的可观测性体系?需要关注哪些关键指标?
考察点:AI服务的SRE意识。
需要分层建立可观测性:
-
业务层:准确率、召回率、用户满意度、幻觉率
-
性能层:推理延迟(P50/P95/P99)、吞吐量(QPS/TPS)、Token消耗
-
系统层:GPU利用率、显存使用、JVM GC情况
-
链路追踪:全链路追踪(如Jaeger),记录从用户请求→向量检索→模型推理→结果返回的完整调用链
日志需记录模型输入输出,便于事后问题定位和效果分析。
四、AI场景下的Java进阶
16. AI推理服务中对象创建频繁,为什么会导致GC抖动?如何排查和优化?
考察点:JVM调优在AI场景的应用。
推理服务中每次请求都会创建大量临时对象(如向量、Prompt字符串、JSON解析对象),频繁触发Minor GC ,导致服务CPU飙升、响应毛刺。
排查思路:监控GC频率和耗时 → 导出堆转储(MAT分析)→ 定位大对象和频繁分配点。优化手段:对象池化 (复用向量对象)、零拷贝序列化 、调整年轻代大小(-Xmn)、使用G1替代CMS减少停顿。
17. 大模型推理中如何管理GPU等异构计算资源?
考察点:对AI基础设施的理解。
DJL等框架支持自动检测GPU并默认使用单GPU推理 。多GPU场景需考虑模型并行 或数据并行。关键点:
-
显存管理:大模型(如70B参数)需要多卡部署,需关注显存分配和碎片化
-
资源隔离:多租户场景下需实现计算资源隔离与公平调度
-
与Java内存的边界 :GPU显存不受JVM管理,需要显式释放(如NDArray.close()),否则会造成Native Memory泄漏
18. Java 8+ 的哪些特性在AI数据处理场景中特别有用?
考察点:对Java新特性与AI场景结合的理解。
-
Stream API:处理AI生成结果(如过滤、映射、聚合),代码简洁高效
-
Lambda表达式:配合CompletableFuture实现异步推理编排
-
var(局部变量类型推断) :简化复杂的泛型类型声明(如
Map<String, List<EmbeddingResult>>) -
Records:作为不可变DTO,适合表示AI请求/响应对象
-
文本块(Text Blocks) :编写多行Prompt模板,可读性大幅提升
五、系统设计与架构
19. 设计一个支持百万级QPS的AI推理结果缓存服务,如何实现?
考察点:高并发AI服务的架构设计。
核心思路是多级缓存:
-
本地缓存(Caffeine) :热点问题结果缓存,毫秒级响应
-
分布式缓存(Redis) :跨实例共享,支持更大规模
-
缓存策略:语义相似度缓存------不仅精确匹配Query,语义相似的Query也可命中缓存(利用向量检索做缓存Key的相似匹配)
-
缓存更新 :模型版本更新时,需批量失效 或版本化缓存Key (如
v1:query_hash)
同时需处理缓存穿透 (空值缓存+布隆过滤器)、缓存击穿 (互斥锁)、缓存雪崩(随机过期时间)。
20. 在一个AIGC内容生成系统中,如何设计异步任务处理架构?
考察点:AI长任务(文生图、文生视频)的系统设计能力。
典型的微服务架构:
-
用户服务:接收请求,创建任务记录,发送消息到队列
-
任务队列(RabbitMQ/Kafka) :解耦请求和处理,支持持久化和重试
-
AI Worker:消费消息,调用模型生成内容,完成后发送结果通知
-
通知服务:推送结果(WebSocket推送/站内信/短信)
关键设计要点:
-
消息可靠性 :开启持久化+确认机制,防止AI服务宕机时消息丢失
-
任务状态管理:任务状态机(pending→processing→success/failed),支持进度查询
-
超时与重试:设置超时时间,失败任务指数退避重试
-
结果存储:生成内容存OSS/对象存储,数据库只存元数据和URL