详细设计任务
- 业务接口的定义
- 领域模型(实体类)的定义
- 数据持久化层的接口定义
- 数据库表的存储设计
- 关键业务设计模式的选用
- 关键业务模块的设计方案
- 关键方法的实现算法
详细设计的好处:
- 对产品的好处
- 更快的产品迭代
- 更好的用户体验
- 更好的用户投诉
- 对技术团队的好处:
- 为构建高并发、高可用和高扩展性的应用打下良好基础
- 产品迭代中越跑越快
- 降低程序推倒重来的概率
- 减少产品运行中的事故
- 对开发者的好处
- 更加清晰、严谨的逻辑思维能力
- 良好的面向对象设计能力
- 有条理、高效的工作,提高成就感
- 更加轻松的面对问题,自信带来愉悦
优秀的详细设计,是在业务场景、开发周期、技术架构等因素综合考虑的结果
优秀的详细设计需要具备的能力:
- 成为一名优秀的程序员
- 良好的面相对象思维
- 懂得如何在设计思路、开发周期、业务需求间取舍
- 熟悉产品技术架构模型
- 深入了解产品行业,熟悉业务细节,并能洞察业务的未来
优秀的判断力来自于经验,但经验来自于错误的判断 —— Fred Brooks
表达设计的方式
- UML
- 文档
- 白板(适合在详细设计之前,对大体方案进行讨论时使用)
- 代码
敏捷开发中的详细设计,提倡设计即编码
详细设计的产物:
- 设计实体类
- 设计前后端调用方式及数据格式
- 设计业务接口(接口的输入输出和实现方式)
- 设计数据库访问层接口
- 设计数据表结构
详细设计的命名规范
- 基本命名规范
- 驼峰命名法
- Java命名规范,使用Checkstyle工具检查
- 有意义的命名
- 具有正确的业务含义
- 避免误导
- 避免使用复杂的单词
- 借用类型表达含义
- 基于约定的命名
- 数据库访问层命名规范:XXDao,insertXX,updateXX,findXX…
- 业务层规范,如XXService
- 控制层规范,如XXAction,XXController,XXActivity…
- 核心业务领域名词
- 特定用途类的名字,如XXVO,XXDTO
- 复数表示法,如XXXs,XXList…
- 基于技术含义的命名
- 抽象类,AbstractXX
- 自定义异常类,XXException
- 测试类,XXTest
- 设计模式,XXFactory,XXVistory
- 队列,XXQueue
- 后台任务,XXTask,XXJob…
- 命名技巧
- 类命名技巧
- 使用名词或名词组合
- 每隔概念对应一个词
- 具有共性的业务使用相同结尾或开头
- 具有对应关系的类使用相同开头
- 业务接口层命名技巧
- 基于约定命名
- 相同动作使用相同动词
- 具有业务含义的接口方法名
- 借用方法返回值、方法参数表达含义
- 数据访问层接口命名技巧
- 基于约定命名
- 使用固定的方法名开头:insert,update,delete,find
- 类命名技巧
善用注释
- 利用TODO 注释标记尚未完成的功能
- 解决方法名过长的问题
- 说明返回值中的空值情况
- 更新代码时,记得更新注释
数据库表的设计原则
- 关系型数据库设计范式
- 1NF对属性的原子性约束
- 2NF对记录的唯一性约束
- 3NF对字段冗余性的约束(更新不频繁的表不需要遵守3NF)
- 关系型数据库的表设计原则
- 统一的命名规范(模块名_表名)
- 混用范式化和反范式化(更新频繁的表使用范式化设计,查询为主的表使用反范式化设计)
- 表的个数越少越好(体现在业务实体的抽象上)
- 一个表的字段越少越好(实体划分越明确,字段越少)
- 联合主键和联合索引个数越少越好
- 关系型数据库表的字段设计
- 统一的命名规范
- 有好的注释
- 字段的顺序
- 选择更小的数据类型
- 尽量避免NULL
- 主键设计:自增int vs GUID
- GUID 比自增int占用更大空间
- GUID进行主键物理排序时,影响IO效率
- 自增int 不利于分库分表
- 自增int不利于数据库迁移
- 非关系型数据库表的设计(以MongoDB为例)
- 适用于内嵌数据的情况
- 数据不经常更新
- 数据最终一致性
- 子文档较小
- 单个文档数据小幅增加
- 快读读取
- 适用于引用数据的情况:
- 数据更新频繁
- 数据中间过程一致性
- 子文档较大
- 文档数据大幅增加
- 快速写入
- MongoDB文档设计原则
- 优先考虑内嵌
- 需要单独访问的对象,不适合在内嵌对象中
- 内嵌数组不能没有上限
- 不要担心应用级别的join
- 反范式设计时,需要考虑读写比重
- 如何设计,取决于应用程序的业务逻辑
- 适用于内嵌数据的情况