阿里巴巴Java开发手册1.7.0(嵩山版)


一、编程规约

(一)命名风格

  1. 所有命名不得以下划线和$开始和结束。

  2. 所有命名不得以拼音或拼音英文混合。

  3. 类名使用UpperCamelCase风格。

  4. 方法名、参数名、成员变量、局部变量都统一使用lowerCamelCase风格。

  5. 常量命名全部大写,单词间用下划线隔开,力求语义表达完整清楚,不要嫌名字长。

  6. 抽象类命名使用 Abstract 或 Base 开头;异常类命名使用 Exception 结尾;

    测试类命名以它要测试的类的名称开始,以 Test 结尾。

  7. 类型与中括号紧挨相连来表示数组。(定义整形数组 int[] arrayDemo。)

  8. 包名统一使用小写,点分隔符之间有且仅有一个自然语义的英语单词。包名统一使用

    单数形式,但是类名如果有复数含义,类名可以使用复数形式。

  9. 杜绝完全不规范的缩写,避免望文不知义。(AbstractClass“缩写”成 AbsClass;condition“缩写”成 condi;Function 缩写”成 Fu)

  10. 在常量与变量的命名时,表示类型的名词放在词尾,以提升辨识度。(动+名词)

  11. Service/DAO 层方法命名规约

    1) 获取单个对象的方法用 get 做前缀。

    2) 获取多个对象的方法用 list 做前缀,复数结尾,如:listObjects。

    3) 获取统计值的方法用 count 做前缀。

    4) 插入的方法用 save/insert 做前缀。推荐save。

    5) 删除的方法用 remove/delete 做前缀。推荐remove。

    6) 修改的方法用 update 做前缀。

(二)常量定义

  1. 不允许出现魔法值(未经过预先定义的值)直接出现在代码中。String key = "Id#taobao_" + tradeId;,其中的字符串就是魔法值。
  2. 在 long 或者 Long 赋值时,数值后使用大写字母 L,不能是小写字母 l。

(三)代码格式

  1. 大括号,单行放一起 { },多行:

    1) 左大括号前不换行。

    2) 左大括号后换行。

    3) 右大括号前换行。

    4) 右大括号后还有 else 等代码则不换行;表示终止的右大括号后必须换行。

  2. if/for/while/switch/do 等保留字与括号之间都必须加空格。

  3. 任何二目、三目运算符的左右两边都需要加一个空格。包括赋值运算符=、逻辑运算符&&、加减乘除符号等。

  4. 采用 4 个空格缩进。

  5. 注释的双斜线与注释内容之间有且仅有一个空格。

  6. 单行字符数限制不超过 120 个,超出需要换行,换行时遵循如下原则:

    1)第二行相对第一行缩进 4 个空格,从第三行开始,不再继续缩进,参考示例。

    2)运算符与下文一起换行。

    3)方法调用的点符号与下文一起换行。

    4)方法调用中的多个参数需要换行时,在逗号后进行。

    5)在括号前不要换行。

  7. 方法参数在定义和传入时,多个参数逗号后面必须加空格。

    下例中实参的 args1,后边必须要有一个空格。

    method(args1, args2, args3);

  8. IDE 的 text file encoding 设置为 UTF-8; IDE 中文件的换行符使用 Unix 格式,不要

    使用 Windows 格式。

  9. 不同逻辑、不同语义、不同业务的代码之间插入一个空行分隔开来以提升可读性。

(四)OOP规约

  1. Object 的 equals 方法容易抛空指针异常,应使用常量或确定有值的对象来调用 equals 。

    正例:"test".equals(object);

    反例:object.equals("test");

    说明:推荐使用 JDK7 引入的工具类 java.util.Objects#equals(Object a, Object b)

  2. 所有整型包装类对象之间值的比较,全部使用 equals 方法比较。

  3. 任何货币金额,均以最小货币单位且整型类型来进行存储。

  4. 浮点数之间的等值判断,基本数据类型不能用==来比较,包装数据类型不能用 equals来判断。

    1. 如上所示 BigDecimal 的等值比较应使用 compareTo()方法,而不是 equals()方法。

      equals()方法会比较值和精度 (1.0 与 1.00 返回结果为 false) ,而 compareTo()则会忽略精度。

    2. 定义数据对象 DO 类时,属性类型要与数据库字段类型相匹配。

    3. 禁止使用构造方法 BigDecimal(double) 的方式把 double 值转化为 BigDecimal 对象。

      说明:BigDecimal(double)存在精度损失风险,在精确计算或值比较的场景中可能会导致业务逻辑异常。

      如:BigDecimal g = new BigDecimal(0.1F); 实际的存储值为:0.10000000149

      正例:优先推荐入参为 String 的构造方法,或使用 BigDecimal 的 valueOf 方法,此方法内部其实执行了

      Double 的 toString,而 Double 的 toString 按 double 的实际能表达的精度对尾数进行了截断。

      BigDecimal recommend1 = new BigDecimal("0.1"); // String

      BigDecimal recommend2 = BigDecimal.valueOf(0.1); // valueOf(double)

    4. 关于基本数据类型与包装数据类型的使用标准如下:

      1) 【强制】所有的 POJO 类属性必须使用包装数据类型。

      2) 【强制】RPC 方法的返回值和参数必须使用包装数据类型。

      3) 【推荐】所有的局部变量使用基本数据类型。

      说明:POJO 类属性没有初值是提醒使用者在需要使用时,必须自己显式地进行赋值,任何 NPE (NullPointerException,空指针异常)问题,或者入库检查,都由使用者来保证。

      正例:数据库的查询结果可能是 null,因为自动拆箱,用基本数据类型接收有 NPE 风险。

      反例:某业务的交易报表上显示成交总额涨跌情况,即正负 x%,x 为基本数据类型,调用的 RPC(Remote Procedure Call) 服务,调用不成功时,返回的是默认值,页面显示为 0%,这是不合理的,应该显示成中划线-。所以包装数据类型

      的 null 值,能够表示额外的信息,如:远程调用失败,异常退出。

      package java_wrapper;
      
      public class Cat {
      String name;
      int month;
      double weight;
      }
      package java_wrapper; public class CatTest {
      public static void main(String[] args) {
      Cat one = new Cat();
      System.out.println("小猫的昵称:"+one.name);
      System.out.println("小猫的年龄:"+one.month);
      System.out.println("小猫的体重:"+one.weight);
      }
      }
      小猫的昵称:null
      小猫的年龄:0
      小猫的体重:0.0
      package java_wrapper;
      
      public class Cat {
      String name;
      Integer month;
      Integer weight;
      } 小猫的昵称:null
      小猫的年龄:null
      小猫的体重:null
    基本类型 包装器类型
    boolean Boolean
    char Character
    int Integer
    byte Byte
    short Short
    long Long
    float Float
    double Double
    1. POJO 类必须写 toString 方法。使用 IDE 中的工具:source> generate toString时,如果继承了另一个 POJO 类,注意在前面加一下 super.toString。

      说明:在方法执行抛出异常时,可以直接调用 POJO 的 toString()方法打印其属性值,便于排查问题。

    2. 禁止在 POJO 类中,同时存在对应属性 xxx 的 isXxx()和 getXxx()方法。框架在调用属性 xxx 的提取方法时,并不能确定哪个方法一定是被优先调用到的。

    3. 类内方法定义的顺序依次是:公有方法或保护方法 > 私有方法 > getter / setter方法。

    4. 循环体内,字符串的连接方式,使用 StringBuilder 的 append 方法进行扩展。

      说明:下例中,反编译出的字节码文件显示每次循环都会 new 出一个 StringBuilder 对象,然后进行 append

      操作,最后通过 toString 方法返回 String 对象,造成内存资源浪费。

      反例:

      String str = "start";

      for (int i = 0; i < 100; i++) {

      str = str + "hello";

      }

    public class DemoStringBuilder2 {
    public static void main(String[] args) {
    StringBuilder bu=new StringBuilder();
    //append方法返回的是this,调用方法的对象bu,this==bu
    bu.append("abc");
    System.out.println(bu); //abc bu.append("abc");
    bu.append("2");
    bu.append("true");
    bu.append("哈喽");
    bu.append("8.8");
    bu.append("abc");
    System.out.println(bu); //abc2true哈喽8.8abc //链式编程:方法返回值是一个对象,可以继续调用方法
    System.out.println("abc".toUpperCase().toLowerCase().toLowerCase());
    bu.append("abc").append(1).append("你好").append(789);
    System.out.println(bu);
    String myStr = bu.toString(); // 返回String对象
    }
    }

(五)日期时间

  1. 【强制】日期格式化时,传入 pattern 中表示年份统一使用小写的 y。

    说明:日期格式化时,yyyy 表示当天所在的年,而大写的 YYYY 代表是 week in which year(JDK7 之后

    引入的概念),意思是当天所在的周属于的年份,一周从周日开始,周六结束,只要本周跨年,返回的 YYYY

    就是下一年。

    正例:表示日期和时间的格式如下所示:

    new SimpleDateFormat("yyyy-MM-dd HH:mm:ss")

    推荐使用java.util.Date;

    import java.util.Date;
    public class SimpleDateFormatDemo {
    public static void main(String[] args) {
    Date currentTime = new Date();
    System.out.println(currentTime); // 输出:Mon Feb 18 10:24:30 CST 2019
    }
    }

    使用format()方法将日期转换为字符串

    import java.text.SimpleDateFormat;
    import java.util.Date;
    public class SimpleDateFormatDemo {
    public static void main(String[] args) {
    Date currentTime = new Date();
    System.out.println(currentTime); // Mon Feb 18 13:53:50 CST 2019
    SimpleDateFormat simpleDateFormat1 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
    SimpleDateFormat simpleDateFormat2 = new SimpleDateFormat("yyyy-MM-dd");
    SimpleDateFormat simpleDateFormat3 = new SimpleDateFormat("yyyy/MM/dd");
    System.out.println(simpleDateFormat1.format(currentTime)); // 输出2019-02-18 13:53:50.629
    System.out.println(simpleDateFormat2.format(currentTime)); // 输出2019-02-18
    System.out.println(simpleDateFormat3.format(currentTime)); // 输出2019/02/18
    }
    }

    使用parse()方法将字符串转换为日期

    SimpleDateFormat simpleDateFormat1 = new SimpleDateFormat("yyyy-MM-dd HH:mm");
    String strDate1 = "2019-02-18 13:58";
    Date date1 = simpleDateFormat1.parse(strDate1);
    System.out.println(date1); // 输出 Mon Feb 18 13:53:50 CST 2019
  2. 【强制】在日期格式中分清楚大写的 M 和小写的 m,大写的 H 和小写的 h 分别指代的意义。

    1) 表示月份是大写的 M;

    2) 表示分钟则是小写的 m;

    3) 24 小时制的是大写的 H;

    4) 12 小时制的则是小写的 h。

  3. **【强制】获取当前毫秒数:System.currentTimeMillis(); **

(六)集合处理

  1. 【强制】判断所有集合内部的元素是否为空,使用 isEmpty()方法,而不是 size()。

    正例:

    正例:
    Map<String, Object> map = new HashMap<>(16);
    if(map.isEmpty()) {
    System.out.println("no element in this map.");
    }

(七)控制语句

  1. 【强制】当 switch 括号内的变量类型为 String 并且此变量为外部参数时,必须先进行 null判断。switch语句必须包含default。

    1. 三目运算符 condition? 表达式 1 : 表达式 2 中,高度注意表达式 1 和 2 在类型对齐时,

      可能抛出因自动拆箱导致的 NPE 异常。

(八)注释规约

  1. 【强制】所有的抽象方法 ( 包括接口中的方法 ) 必须要用 Javadoc 注释、除了返回值、参数、异常说明外,还必须指出该方法做什么事情,实现什么功能。对子类的实现要求,或者调用注意事项,请一并说明。
  2. 【强制】所有的类都必须添加创建者和创建日期。
  3. 【强制】方法内部单行注释,在被注释语句上方另起一行,使用//注释。方法内部多行注释使用/* */注释,注意与代码对齐。
  4. 【参考】谨慎注释掉代码。在上方详细说明,而不是简单地注释掉。如果无用,则删除。

二、MySQL 数据库

(一) 建表规约

  1. 【强制】表达是与否概念的字段,必须使用 is_xxx 的方式命名,数据类型是 unsigned tinyint

    (1 表示是,0 表示否)。

    unsigned是指的无符号,就是没有负数,只能用正数和0,此时unsigned修饰的字段的值可以达到的最大值是原来的最大值加1,即原来一个tinyint字段能表示的范围是:-128 ~ 127,而unsigned修饰的字段范围是 0 ~ 255.

    数据类型 默认范围 unsigned范围
    tinyint -2^7 ~ 2^7-1 0 ~ 2^8-1
  2. 【强制】表名、字段名必须使用小写字母或数字 , 禁止出现数字开头,禁止两个下划线中间只

    出现数字。数据库字段名的修改代价很大,因为无法进行预发布,所以字段名称需要慎重考虑。

    说明:MySQL 在 Windows 下不区分大小写,但在 Linux 下默认是区分大小写。因此,数据库名、表名、

    字段名,都不允许出现任何大写字母,避免节外生枝。

  3. 表名不使用复数名词。

  4. 禁用保留字,如 desc、range、match、delayed 等。

  5. 【强制】主键索引名为 pk_ 字段名;唯一索引名为 uk 字段名 ; 普通索引名则为 idx 字段名。

    说明:pk
    即 primary key;uk
    即 unique key;idx_ 即 index 的简称。

  6. 【强制】小数类型为 decimal,禁止使用 float 和 double。

    说明:在存储的时候,float 和 double 都存在精度损失的问题,很可能在比较值的时候,得到不正确的

    结果。如果存储的数据范围超过 decimal 的范围,建议将数据拆成整数和小数并分开存储。

  7. 【强制】如果存储的字符串长度几乎相等,使用 char 定长字符串类型。

  8. 【强制】 varchar 是可变长字符串,不预先分配存储空间,长度不要超过 5000,如果存储长度

    大于此值,定义字段类型为 text,独立出来一张表,用主键来对应,避免影响其它字段索引效

    率。

  9. 【强制】表必备三字段:id, create_time, update_time。

    说明:其中 id 必为主键,类型为 bigint unsigned、单表时自增、步长为 1。create_time, update_time

    的类型均为 datetime 类型,前者现在时表示主动式创建,后者过去分词表示被动式更新。

  10. 【推荐】表的命名最好是遵循“业务名称_表的作用”。正例:alipay_task / force_project / trade_config

(二)SQL语句

  1. 【强制】不要使用 count(列名)或 count(常量)来替代 count(*),count(*)是 SQL92 定义的标

    准统计行数的语法,跟数据库无关,跟 NULL 和非 NULL 无关。

    说明:count(*)会统计值为 NULL 的行,而 count(列名)不会统计此列为 NULL 值的行。

  2. 【强制】当某一列的值全是 NULL 时,count(col)的返回结果为 0,但 sum(col)的返回结果为

    NULL,因此使用 sum()时需注意 NPE 问题。

    正例:可以使用如下方式来避免 sum 的 NPE 问题:SELECT IFNULL(SUM(column), 0) FROM table;

  3. 【强制】使用 ISNULL() 来判断是否为 NULL 值。

  4. 【强制】对于数据库中表记录的查询和变更,只要涉及多个表,都需要在列名前加表的别名(或表名)进行限定。SQL 语句中表的别名前加 as。

【阿里巴巴Java开发手册1.7.0(嵩山版)】编程规约&MySQL 数据库规约的更多相关文章

  1. 读阿里巴巴Java开发手册v1.2.0之工程结构有感【架构篇】

    首先,把昨天那俩条sql语句的优化原因给大家补充一下,第一条效率极低,第二条优化后的,sql语句截图如下: 经过几个高手的评论和个人的分析: 第一条sql语句查询很慢是因为它首先使用了in关键字查询, ...

  2. 读阿里巴巴Java开发手册v1.2.0之编程规约有感【架构篇】

     不为过去蹉跎,改变当下. 为什么开篇就送这么一句话给大家,我相信很多处于1-3年码龄的哥们儿们,在平时的编码历程中编码的个性可能是多彩的,每个人都有每个人特定的风格,但是我们现在这么随意写,以后这么 ...

  3. 阿里巴巴 Java开发手册1.4.0

    <阿里巴巴Java开发手册1.4.0>下载地址: 下载地址:https://102.alibaba.com/downloadFile.do?file=1528269849853/Java_ ...

  4. 码出高效,阿里巴巴JAVA开发手册1.4.0

    码出高效,阿里巴巴JAVA开发手册1.4.0阅读笔记 一.编程规约(三) 代码格式// 关键词if与括号之间必须有一个空格,括号内的f与左括号,0与右括号不需要空格 if (flag == 0) { ...

  5. 唯品会Java开发手册》1.0.2版阅读

    <唯品会Java开发手册>1.0.2版阅读 1. 概述 <阿里巴巴Java开发手册>,是首个对外公布的企业级Java开发手册,对整个业界都有重要的意义. 我们结合唯品会的内部经 ...

  6. 304902阿里巴巴Java开发手册1.4.0

    转自官网 前言 <阿里巴巴Java开发手册>是阿里巴巴集团技术团队的集体智慧结晶和经验总结,经历了多次大规模一线实战的检验及不断完善,系统化地整理成册,回馈给广大开发者.现代软件行业的高速 ...

  7. 《阿里巴巴Java开发手册1.4.0》阅读总结与心得(五)

    笔者作为一名有数年工作经验的Java程序员,仔细研读了这份手册,觉得其是一份不可多得的好材料.阿里巴巴在发布时所说,“阿里巴巴集团推出的<阿里巴巴Java开发手册(正式版)>是阿里巴巴近万 ...

  8. 《阿里巴巴Java开发手册1.4.0》阅读总结与心得(一)

    前言 下面是阿里对<阿里巴巴 Java 开发手册>(下称<手册>)的介绍: 凝聚了阿里集团很多同学的知识智慧和经验,这些经验甚至是用血淋淋的故障换来的,希望前车之鉴,后车之师, ...

  9. 阿里巴巴java开发手册学习记录,php版

    一.编程规约 (一)命名风格 1.目录使用小写+下划线 home,view,model,admin_view 2.类 UpperCamelCase PhpMailer方法 lowerCamelCase ...

随机推荐

  1. (转载)一篇文章带你分清楚JWT,JWS与JWE

    是JWS(JSON Web Signature),也往往导致了人们对于JWT的误解,但是JWT并不等于JWS,JWS只是JWT的一种实现,除了JWS外,JWE(JSON Web Encryption) ...

  2. Java动态代理和CGLib代理

    本文参考 在上一篇"Netty + Spring + ZooKeeper搭建轻量级RPC框架"文章中涉及到了Java动态代理和CGLib代理,在这篇文章中对这两种代理方式做详解 下 ...

  3. SQL数据库之“TIMESTAMPDIFF(unit,datetime_expr1,datetime_expr2)”

    一.介绍 样本:TIMESTAMPDIFF(unit,datetime_expr1,datetime_expr2) 解析:TIMESTAMPDIFF(格式,开始时间,结束时间) 二.参数解析 格式: ...

  4. Tomcat警告之“资源添加到Web应用程序[]的缓存中,因为在清除过期缓存条目后可用空间仍不足 - 请考虑增加缓存的最大空间”

    原因 缓存不够,可以将其缓存调大 解决办法: 在 /conf/context.xml 的 前添加以下内容: <Resources cachingAllowed="true" ...

  5. ros中关于节点、话题、服务以及自定义消息等在终端中的常用命令

    以下面的计算力图说明 节点相关常用命令 在终端中查看项目中有哪些节点命令:rosnode list 有了节点信息想要查看节点中到底发布订阅了哪些话题,作为服务端服务类型或者作为客户端需要的服务类型以上 ...

  6. python学习笔记(三)——函数

    函数定义 def 函数名(形参 . . . ) 函数体 1. 函数参数 返回值:可以有一个或多个 形参:支持默认形参.关键字形参.可变参数形参等 1.1 必须参数 调用时传入的参数必须与定义时相同. ...

  7. 14_Nonlinear Basic Feedback Stabilization_非线性系统稳定性设计

    非线性系统线性化的方式:泰勒展开近似线性化(2_线性化_泰勒级数_泰勒公式_Linearization).反馈线性化,本文使用的是反馈线性化 从图中可知道输入u非常大达到了900多,所以直接使用u消去 ...

  8. 【babel+小程序】记“编写babel插件”与“通过语法解析替换小程序路由表”的经历

    话不多说先上图,简要说明一下干了些什么事.图可能太模糊,可以点svg看看 背景 最近公司开展了小程序的业务,派我去负责这一块的业务,其中需要处理的一个问题是接入我们web开发的传统架构--模块化开发. ...

  9. React系列——websocket群聊系统在react的实现

    前奏 这篇文章仅对不熟悉在react中使用socket.io的人.以及websocket入门者有帮助. 下面这个动态图展示的聊天系统是用react+express+websocket搭建的,很模糊吧, ...

  10. 手机上无法显示Toast信息

    关于手机上无法显示Toast信息, 是因为手机上的权限没有开, 在应用管理处将所有权限都打开,就可以显示了.