AI理解与应用
AI理解与应用
一、AI理解
最近人工智能大会上有提到一个重要观点:人类互联网上已知的数据已经被用光了。那AI如何进步?主要通过模型的微调,但给RAG的知识库并不是越多越好,这一块需要基于Transformer神经网络的理解。在日常使用中,只要给好提示词,做模型时给好系统提示词和知识库,就能得到一个满足日常使用的智能体。
AI对程序员的影响
近期关于AI取代程序员的话题很多。从2023年ChatGPT被认为是鸡肋,到DeepSeek出世,再到各家模型的推出,AI的进步呈指数级增长。无疑我们需要拥抱AI,学会使用它。
关于AI取代程序员,在有一定规模公司做项目的都会明白,目前不太可能。程序员更重要的是对业务能力的理解,对不同的业务采用不同的方案,以及甲方、产品、开发之间的沟通。一些甲方自己都说不清楚自己的需求,如果给他一个AI,他能自己做出项目吗?包括后期的维护、故障修复等问题。所以,一些对业务梳理能力差、只会CRUD的程序员的生存空间会被压缩。而理解业务的程序员+AI提效反而是一种机会。
二、RAG技术
RAG原理
RAG(Retrieval-Augmented Generation,检索增强生成)分为检索前和检索后两个部分:
-
检索前:将文本分割成小块,用向量模型将文本块嵌入成向量,建立索引,给大模型提示,告诉模型要根据后续搜索到的上下文来回答问题。
-
检索后:将用户的查询也转换成向量,根据索引查询向量,找到前K个最相关的结果,再从向量数据库中找到对应的文本块,放入大模型,大模型根据这部分总结输出。
这套机制很像相似度算法(余弦相似度),通过索引和文本块的方式也很像ES和MongoDB的搜索方式,所以有些教程采用MongoDB作为向量数据库。
RAG特点
从AI的知识库中检索答案并给用户回答,天然无法理解私域问题,无法直接用于企业。
RAG优化
- 多路召回:召回环节可以用多路召回,但会有截断和分数对齐的问题,所以需要重排序。
- 模型微调:根据系统的回答情况进一步微调模型。
幻觉问题
幻觉是指生成结果和数据源对不上,可能的原因包括:
- 训练的数据和原数据有偏差
- 编码器和解码器在理解token时出错
- 用户问的问题超过了大模型的认知范围
幻觉的解决
- 优化数据源和模型的逻辑,找到更精准的数据,删除容易误导模型的数据
- 加规则,当模型输出结果后,让它自己再思考一次,判断是否与上下文一致
- 集成知识图谱,不止靠向量数据库匹配,召回时既要看文档也要看知识图谱,通过图谱的结构化数据减少幻觉
如何微调模型
模型懂得多不代表精,有时候多的反而会影响输入。例如在调旅游数据时,除了景区的相关介绍,还清洗了用户的相关数据,包括用户的收藏景区、评分、评论等,以及用户间余弦相似度的推荐文件,将用户之间对景区的喜爱相似度数据也喂给千问。
训练参数(旅游场景适配)
- 批次大小(batch size):8~16(根据显存调整)
- 学习率:1e-4~1e-5(旅游数据量通常<10万条,小学习率避免过拟合)
- 训练轮数(epoch):3~5(验证集loss上升即停止,防止过拟合)
- 梯度累积:4(提升训练稳定性)
RAG的优势
- 减少幻觉:错误率从传统LLM的40%+降至15%以下
- 知识实时更新:无需重新训练模型,直接更新外部知识库
- 精准领域适配:针对专业领域(医疗、金融等)提供定制化知识支撑
- 可追溯性:回答内容有明确来源,便于审计和验证
关键实现要点与注意事项
- 知识库质量是基础:“垃圾进垃圾出”,低质量知识库会导致防不胜防的幻觉
- 版本控制与更新:
- 为知识库建立版本号,记录更新时间
- 在回答中包含"信息时效性说明",提醒用户注意内容更新状态
- 幻觉监控与迭代:
- 建立"幻觉检测日志",记录被拦截的幻觉案例
- 定期分析幻觉产生模式,针对性优化检索策略和提示词
三、MCP技术
MCP(Model Context Protocol)更像是一种插件,为AI系统与外部工具交互提供标准接口,让AI能访问第三方的工具和数据。
四、Agent技术
Agent是决定做什么、怎么做的智能体,主要包含以下组件:
- 大模型:负责理解目标、逻辑推理、生成指令
- 记忆系统:存储历史对话、任务状态,提供上下文连续性
- 规划模块:将目标拆解为执行步骤,制定行动计划
- 工具接口:调用API、操作数据库、执行外部程序等
五、Prompt工程
Prompt编写技巧
- 明确AI的角色:比如"你是一位Java程序员,只会写Bug"
- 提供细节要求:比如"写一篇300字的文章,突出专业性"
- 拆解任务:比如"先需求分析,再技术选型,最后编码实现,并生成项目总结"
- 提供示例:比如"模仿李白的《静夜思》,创作一首表达思乡之情的五言诗歌"
AI提高开发效率
使用AI coding开发时,需要把任务的需求捋清楚,包括可能需要的上下文。除了提示词之外,可以配置一些rule规则。例如,为了防止误开发,可以提前把系统规则限制好,比如开发动代码前,需要写一份执行计划的大纲,说明要动哪些代码、要写什么东西,等同意以后才能动代码。也可以使用MCP,在Agent需要数据库相关数据和表结构的时候,让它能拿到数据库的表结构。
把AI当自己的实习生一样,跟它讲明白要完成什么样的任务。
六、学习AI的途径
1. 学习途径
主要通过公众号和CSDN了解AI前沿技术,包括短视频。比如最近看到Gemini 3,就会去平台搜索,会有很多博主分享使用的过程和它的厉害之处。
2. 优质博主
- 个人博主:鱼皮、阿华等
- 技术团队:黑马、美团技术团队、腾讯技术团队、阿里内容分享
- 有赞coding近期都是关于AI方面的知识
3. 行业趋势
- 国内的一些大项目都在往国产化转型,这是国家政策方向
- AI的冲击,基本很多项目中都有嵌入AI的相关模块,问答型的也好,操作型的
- 传统项目向数字化转型
- 电商向新零售全面发展,资金链、物流、信息流的整合,其他传统项目也在借鉴新零售概念进行整合
4. 程序员在AI时代应该锻炼的技能
- 合理使用AI coding的能力,对自己开发效率进行提效
- AI应用开发是最重要的亮点
- 使用AI IDE时,要会设置rule规则并提供好上下文
- AI应用要会合理解决AI模型"幻觉"、数据偏见等行业痛点
七、DDD领域驱动设计
DDD理解
DDD(Domain-Driven Design,领域驱动设计)是以业务为核心的建模方式,核心逻辑是"让技术设计贴合业务本质"。先梳理清楚业务领域的核心概念、规则和流程,再基于业务模型设计技术架构。
核心概念包括:
- 限界上下文
- 聚合根
- 领域服务
- 领域事件
这种模式比较适用于像有赞这种电商项目,因为业务流程比较复杂,涉及库存、订单、支付、物流、售后等,项目比较大,需要多部门协作,每个部门的每个小组负责几块领域,后期也需要迭代维护和业务变更。
微服务拆分依据
微服务拆分主要基于DDD思想,按业务边界和数据独立性进行垂直拆分。将单体应用拆分成用户、景区、订单、搜索、推荐等6个核心微服务,依据主要有三点:
-
业务耦合度:
- 景区服务主要负责信息展示,是读多写少的场景
- 订单服务涉及支付和库存扣减,是高并发写的场景
- 将它们拆分,可以针对性地对景区服务做缓存优化,对订单服务做分布式锁和流量控制,互不影响
-
数据边界:
- 每个服务拥有独立的数据库表
- 订单表只属于订单服务,景区表只属于景区服务
- 避免跨库Join的复杂性,也为后续的分库分表打下基础
-
技术栈差异:
- 搜索和推荐模块引入了Elasticsearch和Python的机器学习算法
- 这部分技术栈和传统CRUD业务差异很大,计算资源消耗也不同
- 必须独立拆分出来,避免拖慢主业务接口
边界不清晰的决策
例如购物车模块:
- 购物车与用户强绑定,在中小型电商项目中,数据耦合度高,业务逻辑简单,可能会放在用户模块
- 但在中大型电商中,购物车是频繁访问的操作,而且涉及库存、优惠券匹配,可能会单独拆分成一个购物车服务
八、数据库迁移
达梦和MySQL迁移的兼容性
需要处理以下兼容性问题:
- SQL语法的兼容
- 强制大小写问题
- 数据类型兼容
- 精度丢失
- 函数的兼容
需要依赖中间表进行二次转换。
迁移方式
部分增量数据是线上正常运行的,基于达梦DMHS(数据同步工具)实现"全量初始化 + 增量同步 + 秒级割接",全程不影响线上运行。会在晚上2点到6点进行更新,停机做数据的迁移。
迁移验证
- 行数校验+日志打印
- 抽样检验
- 迁移部分流量到新数据库
- 监控系统看有没有报错
九、消息队列选型
RabbitMQ vs RocketMQ
RabbitMQ特点:
- 部署简单,性能高
- 吞吐量只支持万级的TPS
RocketMQ特点:
- Java开发,在Java项目中对JVM的支持更好
- 性能支持微秒级别,完全够使用
- 支持分布式集群+十万级别的TPS吞吐
- 比较适合中大型项目开发
- 后期维护的方案很多,因为是国内的,有很多相关文档
十、Dubbo框架
核心组件
Dubbo的核心组件分为四个部分:
- 注册中心
- 服务消费方
- 服务提供方
- 监控中心
工作流程
- 服务提供方启动时,会去注册中心注册自己的服务器地址、端口和基本信息
- 服务消费方会去找注册中心订阅服务列表
- 注册中心推送服务
- 监控中心会定时采集服务调用方和消费方的次数、时间、方法等
底层原理
底层原理分成了十层,但最关键的通讯是基于动态代理,是代理之间进行的网络通讯。默认是JDK动态代理,但也支持CGLIB。近年来JDK版本更新,JDK的效率已经比CGLIB要好很多了,而且初次启动不用加载很多子类的字节码文件,一般都使用JDK动态代理。
十一、自研RPC框架
RPC本质
实现一个不依赖任何开源工具的自研RPC框架,RPC的本质是"客户端透明调用服务端方法"。
全链路核心流程
客户端代理调用 → 序列化 → 服务发现 → 网络传输 → 服务端解码 → 反射调用 → 响应序列化 → 网络回传 → 客户端解码
详细流程
客户端
- 动态代理拦截本地方法调用 → 封装RPC请求(方法名、参数、服务名)
- 自研序列化:将请求对象转为字节流(自定义协议)
- 自研服务发现:从本地缓存的服务地址列表中选一个(轮询负载)
- 自研网络通信:通过Java Socket发送请求字节流
服务端
- 监听Socket端口:接收客户端请求字节流
- 自研反序列化:将字节流还原为RPC请求对象
- 反射调用:根据请求中的服务名/方法名,调用目标方法
- 序列化响应结果:将方法返回值转为字节流
- 网络回传:通过Socket将响应字节流返回客户端
客户端
- 反序列化响应:还原返回值
- 代理对象将返回值返回给调用方
核心实现
-
客户端动态代理层:用JDK动态代理拦截服务接口的方法调用(仅依赖Java反射包,无额外依赖)。拦截后,把调用的核心信息——服务名、方法名、参数类型、参数值封装成统一的RPC请求对象,这一步的核心是屏蔽远程调用细节,让用户无感知。
-
序列化与协议层:放弃所有开源序列化工具,用Java原生的ObjectInputStream/ObjectOutputStream实现对象和字节流互转;同时自定义极简二进制通信协议:加4字节魔数(防粘包)、1字节版本号(兼容后续升级)、8字节请求ID(匹配请求与响应)、4字节数据长度(解决拆包),最后拼接序列化后的请求体,保证两端编解码规则一致。
-
服务注册与发现层:服务端启动时,将"服务名 - 本机IP + 端口"写入ConcurrentHashMap,再写入本地文件做持久化;客户端启动时读取该文件,拉取服务地址列表到本地缓存,再实现轮询负载均衡,定时刷新本地缓存适配服务端地址变更。
-
网络通信层:基于Java原生Socket(先实现BIO模式满足基础需求)。客户端通过Socket连接选中的服务端地址,发送封装好的协议字节流;服务端启动ServerSocket监听端口,每接一个请求就开一个新线程处理,避免单线程阻塞,保证基础并发能力。
-
服务端处理层:服务端线程读取字节流后,先解析自定义协议(校验魔数、版本号,读取数据长度和请求体),反序列化成RPC请求对象;再通过反射,根据请求中的服务名找到内存中注册的服务实现类,按方法名+参数类型匹配目标方法并调用,获取返回结果后封装成RPC响应对象,序列化后按相同协议回传给客户端。
-
客户端响应处理层:客户端读取服务端返回的字节流,反序列化成响应对象,判断调用是否成功——成功则返回结果,失败则抛出异常,完成整个调用闭环。
十二、AI编程工具
接触过的IDE
从IDEA最开始的插件通义千问,再到后面的Trae和Cursor都有使用。
模型与推荐系统的结合
使用线上API,但千问提供自定义模型。在阿里控制台,可以通过自己的文件上传来训练推荐能力。主要提供以下文件和上下文:
- 景区的介绍文件
- 用户行为分析:用户侧有评论系统,在没模型时,推荐基于相似算法(用户A和用户B的相似度,二维矩阵),根据评论情绪值、打分、景区热度做的文件
- 系统提示词:告诉模型要做什么任务,推荐出怎么样的景区,以什么为优先级(地址、分类等)
推荐系统升级
原方案:加权算法 & 相似度
算分 → 排序 → 返回列表
新方案:RAG(检索增强生成)
这是改动最大的地方,也是简历最大的亮点。不要只做"猜你喜欢",要做"AI旅游顾问"。
-
向量化(Embedding):利用Qwen的Embedding接口,将所有景区的INTRO(简介)和TAGS转成向量,存入向量数据库(如Milvus或简单的FAISS,甚至存成文件)
-
语义搜索:当用户搜索"适合带孩子玩水的地方"时,将这句话转向量,在数据库中搜出最相似的Top 5景区
-
生成推荐理由:将搜出的景区信息喂给Qwen,让它生成一段推荐语

