本文是对阿里插件中规约的详细解释一,关于插件使用,请参考这里

1. ArrayList的subList结果不可强转成ArrayList,否则会抛出ClassCastException异常。 说明:禁止强转,如果需要用到集合特性方法,请新建一个集合,然后置入sublist,new 集合(sublist结果)。

Negative example:
List<String> list = new ArrayList<String>();
list.add("22");
//warn
List<String> test = (ArrayList<String>) list.subList(0, 1); Positive example:
List<String> list2 = new ArrayList<String>(list.subList(0, 1));

2. iBATIS自带的queryForList(String statementName,int start,int size)不推荐使用

3. long或者Long初始赋值时,必须使用大写的L,不能是小写的l,小写容易跟数字1混淆,造成误解。 (注:规约)

Negative example:
//It is hard to tell whether it is number 11 or Long 1.
Long warn = 1l; Positive example:
Long notwarn = 1L;

4. Map/Set的key为自定义对象时,必须重写hashCode和equals。

注:两个相同的对象,要求hashcode必须相同,但反之无此要求。因为用hashcode的本意在于提高效率,
所以有时在比较对象时(比如map的contain等),会先比较hashcode,如果hashcode不等,就直接返回结果
关于hashCode和equals的处理,遵循如下规则:  
1) 只要重写equals,就必须重写hashCode。  
2) 因为Set存储的是不重复的对象,依据hashCode和equals进行判断,所以Set存储的对象必须重写这两个方法。  
3) 如果自定义对象作为Map的键,那么必须重写hashCode和equals。

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

6. POJO类中的任何布尔类型的变量,都不要加is,否则部分框架解析会引起序列化错误

public class DemoDO{
Boolean success;
Boolean delete;
}

7. POJO类必须写toString方法。(约定)

使用工具类source> generate toString时,如果继承了另一个POJO类,注意在前面加一下super.toString。 说明:在方法执行抛出异常时,可以直接调用POJO的toString()方法打印其属性值,便于排查问题。

public class ToStringDemo extends Super{
private String secondName; @Override
public String toString() {
return super.toString() + "ToStringDemo{" + "secondName='" + secondName + '\'' + '}';
}
} class Super {
private String firstName; @Override
public String toString() {
return "Super{" + "firstName=" + firstName + '\'' + '}';
}
}

8. SimpleDateFormat 是线程不安全的类,一般不要定义为static变量,如果定义为static,必须加锁,或者使用DateUtils工具类。

说明:如果是JDK8的应用,可以使用Instant代替Date,LocalDateTime代替Calendar,DateTimeFormatter代替SimpleDateFormat,
官方给出的解释:simple beautiful strong immutable thread-safe。 Positive example 1:
private static final String FORMAT = "yyyy-MM-dd HH:mm:ss";
public String getFormat(Date date){
SimpleDateFormat dateFormat = new SimpleDateFormat(FORMAT);
return sdf.format(date);
} Positive example 2:
private static final SimpleDateFormat SIMPLE_DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
public void getFormat(){
synchronized (sdf){
sdf.format(new Date());
….;
} Positive example 3:
private static final ThreadLocal<DateFormat> DATE_FORMATTER = new ThreadLocal<DateFormat>() {
@Override
protected DateFormat initialValue() {
return new SimpleDateFormat("yyyy-MM-dd");
}
};

9. 不允许任何魔法值(即未经定义的常量)直接出现在代码中

Negative example:
//Magic values, except for predefined, are forbidden in coding.
if(key.equals("Id#taobao_1")){
//...
} Positive example:
String KEY_PRE = "Id#taobao_1";
if(key.equals(KEY_PRE)){
//...
}

10. 不能使用过时的类或方法。

说明:java.net.URLDecoder 中的方法decode(String encodeStr) 这个方法已经过时,应该使用双参数decode(String source, String encode)。
接口提供方既然明确是过时接口,那么有义务同时提供新的接口;作为调用方来说,有义务去考证过时方法的新实现是什么。

11. 不能在finally块中使用return,finally块中的return返回后方法结束执行,不会再执行try块中的return语句。

注:这里阿里没有解释清楚,其实指的是如果try中语句出现异常,因为finally的return语句,会造成异常丢失的情况

Negative example:
public static Long readFileLength(String fileName) {
try {
File file = new File(fileName);
RandomAccessFile randomAccessFile = new RandomAccessFile(file, "r");
return randomAccessFile.length();
} catch (Exception e) {
logger.error(e.getMessage(), e);
} finally {
countDownLatch.countDown();
return 0L;
}
}

12. 不要在foreach循环里进行元素的remove/add操作,remove元素请使用Iterator方式。

注:会造成异常

 Negative example:
List<String> originList = new ArrayList<String>();
originList.add("22");
for (String item : originList) {
//warn
list.add("bb");
}

13. 中括号是数组类型的一部分,数组定义如下:String[] args  (注:约定)

14. 事务场景中,抛出异常被catch后,如果需要回滚,一定要手动回滚事务。

注:spring中@Transactional默认当抛出RuntimeException时会自动回滚

Positive example 1:
/**
* @author caikang
* @date 2017/04/07
*/
@Service
@Transactional(rollbackFor = Exception.class)
public class UserServiceImpl implements UserService {
@Override
public void save(User user) {
//some code
//db operation
}
} Positive example 2:
/**
* @author caikang
* @date 2017/04/07
*/
@Service
public class UserServiceImpl implements UserService {
@Override
@Transactional(rollbackFor = Exception.class)
public void save(User user) {
//some code
//db operation
}
} Positive example 3:
/**
* @author caikang
* @date 2017/04/07
*/
@Service
public class UserServiceImpl implements UserService {
@Autowired
private DataSourceTransactionManager transactionManager; @Override
@Transactional
public void save(User user) {
DefaultTransactionDefinition def = new DefaultTransactionDefinition();
// explicitly setting the transaction name is something that can only be done programmatically
def.setName("SomeTxName");
def.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED); TransactionStatus status = transactionManager.getTransaction(def);
try {
// execute your business logic here
//db operation
} catch (Exception ex) {
transactionManager.rollback(status);
throw ex;
}
}
}

15. 使用CountDownLatch进行异步转同步操作,每个线程退出前必须调用countDown方法,线程执行代码注意catch异常,确保countDown方法可以执行,避免主线程无法执行至await方法,直到超时才返回结果。 说明:注意,子线程抛出异常堆栈,不能在主线程try-catch到。

注:关于CountDownLatch,用于需子线程结束主线程才能继续的场景,可以参考这里

    /**
* @author caikang
* @date 2017/04/07
*/
public class CountDownExample {
public void operate(CountDownLatch countDownLatch){
try{
System.out.println("business logic");
}catch (RuntimeException e){
// do something
}finally {
countDownLatch.countDown();
}
}
}

16. 使用工具类Arrays.asList()把数组转换成集合时,不能使用其修改集合相关的方法,它的add/remove/clear方法会抛出UnsupportedOperationException异常。

注:看Arrays.asList源码可以知道这个方法生成的是Arrays里面的一个size固定的内部类ArrayList,而不是常用的ArrayList,虽然它也实现List接口

Positive example:
List<String> t = Arrays.asList("a","b","c");
//warn
t.add("22");
//warn
t.remove("22");
//warn
t.clear();

17. 使用集合转数组的方法,必须使用集合的toArray(T[] array),传入的是类型完全一样的数组,大小就是list.size()

Negative example:
Integer[] a = (Integer [])c.toArray(); Positive example:
Integer[] b = (Integer [])c.toArray(new Integer[c.size()]);

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

 1) 所有的POJO类属性必须使用包装数据类型。
 2) RPC方法的返回值和参数必须使用包装数据类型。
 3) 所有的局部变量推荐使用基本数据类型。 说明:POJO类属性没有初值是提醒使用者在需要使用时,必须自己显式地进行赋值,任何NPE问题,或者入库检查,都由使用者来保证。

注:NPE:NullPointerException,这样写是为了统一,用户显式赋值,要比有默认值为前提不容易出错

    public class DemoDO {
String str;
Integer a;
}

19. 创建线程或线程池时请指定有意义的线程名称,方便出错时回溯。创建线程池的时候请使用带ThreadFactory的构造函数,并且提供自定义ThreadFactory实现或者使用第三方实现。

    ThreadFactory namedThreadFactory = new ThreadFactoryBuilder()
.setNameFormat("demo-pool-%d").build();
ExecutorService singleThreadPool = new ThreadPoolExecutor(1, 1,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>(1024), namedThreadFactory, new ThreadPoolExecutor.AbortPolicy()); singleThreadPool.execute(()-> System.out.println(Thread.currentThread().getName()));
singleThreadPool.shutdown(); public class TimerTaskThread extends Thread {
public TimerTaskThread(){
super.setName("TimerTaskThread"); …
}

20.  包名统一使用小写,点分隔符之间有且仅有一个自然语义的英语单词。包名统一使用单数形式,但是类名如果有复数含义,类名可以使用复数形式

com.alibaba.mpp.util / com.taobao.tddl.domain.dto

最新文章

  1. 使用SQLServer同义词和SQL邮件,解决发布订阅中订阅库丢失数据的问题
  2. 除非Microsoft FTP 服务(FTPSVC)正在运行,否则无法启动FTP站点。服务目前已停止
  3. LeetCode 118 Pascal&#39;s Triangle
  4. [WPF]有滑动效果的进度条
  5. JavaEE5 Tutorial_Jsp,EL
  6. JAVA操作LDAP总结
  7. JSP简单练习-数组应用实例
  8. oracle用户权限的问题
  9. HDU 4008 Parent and son
  10. Linux如何查找处理文件名后包含空格的文件
  11. vue项目中解决type=”file“ change事件只执行一次的问题
  12. github下载项目代码到本地,不能运行 本地改完代码 再上传
  13. leetcode 153. Find Minimum in Rotated Sorted Array 、154. Find Minimum in Rotated Sorted Array II 、33. Search in Rotated Sorted Array 、81. Search in Rotated Sorted Array II 、704. Binary Search
  14. 微软开放 6 万项 Linux 专利,有哪些是我们该注意的?
  15. 深入理解ASP.NET MVC(7)
  16. Idiom: a Lot on my Plate
  17. spring装配注解(IOC容器加载控制)ComponentScan及ComponentScans使用
  18. 【转】Mysql学习---SQL的优化
  19. 【技巧总结】Penetration Test Engineer[2]-Information gathering
  20. Nodejs学习笔记(二)--- 操作MongoDB数据库

热门文章

  1. 前端设置cookie,以及jQuerycookie的使用
  2. 恢复oracle的回收站的所有的表
  3. C++面向对象类的实例题目二
  4. 用bat写的一个小病毒
  5. alias这个命令还是很有用的
  6. CF1030F Putting Boxes Together
  7. 断电操作导致的jboss项目部署失败------从早上九点一直到下午4点才解决
  8. scala的map的操作
  9. 《Head First Servlets & JSP》-2-概述
  10. 【Android小技巧】android 按键如何能自动触发点击