Java开发编码规范重点整理

1.命名风格

  • 代码中的命名均不能以下划线或者美元符号开头,也不能以其结尾
  • 类名使用UpperCamelCase风格,如:UserService
  • 方法名、参数名、成员变量、局部变量都统一使用lowerCamelCase风格,必须遵循驼峰式命名规则
  • 常量名全部大写,单词间用下划线隔开
  • 包名统一使用小写
  • 接口和接口的实现类命名:UserService和UserServiceImpl
  • 枚举类类名建议带上Enum后缀,枚举成员名称需要全大写,单词间用下划线隔开
  • 代码中的浮点数必须使用BigDecimal类型,禁止使用float和double
  • 各层命名规约:
    • Service层方法命名规约,服务接口的名称按照动作 + 资源表 + 业务标识 进行标识,采用驼峰风格,其中动作包括get、put、post、delete对应查询、修改、增加和删除
      • 获取单个对象用get
      • 获取多个对象的方法用get做前缀,复数形式结尾如:listObjects
      • 插入的方法用post做前缀
      • 删除的方法用delete做前缀
      • 修改的方法用put做前缀
    • Dao层:
      • 获取单个对象用get
      • 获取多个对象的方法用list做前缀,复数形式结尾如:listObjects
      • 获取统计值的方法用count做前缀
      • 插入的方法用insert做前缀
      • 删除的方法用delete做前缀
      • 修改的方法用update做前缀

2.常量定义

  • 不允许任何魔法值(即未预先定义的常量)直接出现在代码中
  • 在long或者Long赋值时,数值使用大写的L,不能是小写的l
  • 尽量不要使用一个常量类维护所有的常量,要按常量的功能进行分类

3.代码格式

  • 大括号的使用约定
    • 如果是大括号内为空,那么就简洁的写成{}即可,不需要换行
  • 在if或者运算符等左右都要加空格如:int count = 0、if () {}…
  • 注释的双斜线与注释内容之间有且仅有一个空格
  • 方法参数在定义和传入时,多个参数逗号后边必须加空格
  • 不同逻辑、不同语义、不同业务的代码之间插入一个空行分割开来以提升可读性

4.OOP规约

  • Object的equals方法容易抛空指针异常,应使用常量或者有确定有值的对象来调用equals
  • 所有的相同类型的包装类对象之间的比较,全部使用equals方法比较
  • 所有的pojo类属性全部必须使用包装类数据类型,避免NPE风险
  • 禁止在pojo类中,同时存在对应属性的isXxx和getXxx
  • 使用索引访问用String的split方法得到的数组时,需做最后一个分隔符有无内容的检查,否则会有抛IndexOutOfBoundException的风险
  • 任何类、方法、参数、变量、严格控制访问范围,过于宽泛的访问范围,不利于模块之间的解耦

5.集合处理

  • 只要重写了equals,就必须重写hashcode
  • 使用集合转数组的方法,必须使用集合的toArray(T[] array),传入的是类型完全一样的数组,大小就是list.size()
  • 使用工具类Arrays.asList()把数组转换成集合时,不能使用其修改集合的相关方法,它的add/remove/clear方法会抛出UnsupportedOperationException异常
  • 不要在foreach循环中进行元素的remove/add操作,remove元素请使用Iterator方式,如果发生并发操作,需要对Iterator对象加锁
  • 集合初始化时,指定集合初始值大小
  • 推荐使用entrySet遍历Map类集合kv,而不是keySet遍历方式,因为keySet遍历,其实是遍历了两次,一次是转为Iterator对象,另一次是从hashmap中取出key所对应的value,而entrySet只遍历了一遍就把key和value都放到了entry中,效率更加的高。
  • 利用set元素唯一的特性,可以快速对一个集合进行去重操作,避免使用list的contains方法进行遍历、对比、去重操作

6.并发处理

  • 获取单例对象需要保证线程安全,其中的方法也要保证线程安全
  • 创建线程或者线程池时请指定有意义的线程名称,方便出错时回溯
  • 线程资源必须通过线程池提供,不允许在应用中自行显式创建线程,使用线程池的好处是减少在创建和销毁线程上所消耗的时间以及系统资源的开销,解决资源不足的问题。如果不适用线程池,有可能造成系统创建大量的同类线程而导致消耗完内存或者”过度切换的问题“
  • simpleDateFormat是非线程安全的类,一般不要定义为static变量,如果定义为static必须加锁,或者使用DateUtils,也推荐如下写法:
private static final ThreadLocal<DateFormat> df = new ThreadLocal<DateFormat>(){
	@Override
	protected DateFormat initiaValue(){
		return new SimpleDateFormat("yyyy-MM-dd");
	}
}

// 注:如果是jdk8的应用,可以使用Instant代替Date, LocalDateTime代替Calendar, DateTimeFormatter代替SimpleDateFormat, 官方给出的解释为:simple beautiful strongimmutable thread-safe
  • 高并发时,同步调用应该去考量锁的性能损耗,能用无锁的数据结构就不要用锁,能锁区块就不要锁整个方法体,能用对象锁就不要用类锁
  • 对多个资源,数据库表,对象同时加锁时,需要保持一致的加锁顺序,否则就可能会造成死锁。

7.控制语句

  • 在一个switch块内,每个case要么通过break/return等来终止,要么注释说明程序将继续执行到哪一个case为止,在一个switch块内,都必须包含一个default语句并且放在最后,即使空代码
  • 在if/else/for/while/do语句中必须使用大括号,即使只有一行代码,避免采用单行的编码方式
  • 在高并发场景中,避免使用“等于”判断作为中断或者退出的条件,如:判断剩余奖品的数量等于0时终止发放奖品,但因为并发处理错误导致奖品数量瞬间变成了负数,这样的话,活动就没有办法终止了。

8.注释规约

  • 类、类属性、类方法的注释都必须使用Javadoc规范
  • 所有的抽象方法(包括接口中的方法) 必须要用javadoc注释,除了返回值、参数、异常说明之外,还必须指出该方法做什么事情,实现了什么功能
  • 所有的类都必须添加创建者和创建日期
  • 所有的枚举类型字段都必须要有注释,说明每个数据项的用途

9.异常的处理

  • java类库中定义的可以通过预检查方式规避的RuntimeException异常不应该通过catch的方式来处理。比如:NullPointerException,IndexOutOfBoundException等等
  • 异常不要用来做流程控制,条件控制
  • 不要再finally块中使用return
  • 防止NPE,是程序员的基本修养,注意NPE产生的场景:
    • 返回类型为基本数据类型,return包装数据类型的对象时,自动拆箱有可能产生NPE。
    • 数据库的查询结果可能为null
    • 集合里的元素即使isNotEmpty,取出的数据元素也可能为null
    • 远程调用返回对象时,一律要求进行空指针判断,防止NPE
    • 对于session中获取的数据,建议进行NPE检查

10.日志规约

  • 应用中不可直接使用日志系统(Log4j、Logback)中的API,而应该依赖使用日志框架SLF4J中的API,使用门面模式的日志框架,有利于维护和各个类的日志处理方式统一。
  • 日志文件至少保存15天,因为有些异常具备以周为频次发生的特点

11.其他

  • 注意Math.random()这个方法返回是double类型,注意取值的范围0≤ x <1(能够取到零值,注意除零异常),如果想获取整数类型的随机数,不要将x放大10的若干倍然后取整,直接使用Random对象的nextInt或者nextLong方法
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值