package test;
import java.util.ArrayList;
import java.util.List;
/**
* DEMO 模拟
* 异常描述:
* 1.主方法调用私有方法:
* 2.私有方法内部对对象的属性进行处理
* 3.主方法使用对象属性,结果为空
*/
public class Test {
private List<Integer> integerList;
public List<Integer> getIntegerList() {
return integerList;
}
public void setIntegerList(List<Integer> integerList) {
this.integerList = integerList;
}
/**
* 场景模拟
* 1.integerList1 模拟问题异常场景
* 2.integerList2 模拟问题修复场景
* 异常疑惑
* 1.为何仅仅是移动了取值的顺序就可以解决取值为空的场景?
* 2.为何开发时没有发现会出现此类问题?
* 异常分析
* 1.主方法与从方法进行的是值传递,又因为是引用数据类型,从方法内部的修改会影响到主方法的属性,因为指向同一个堆空间地址
* 2.特殊场景:
* a.主方法中对象的属性为null,主方法中对象的属性 integerList 在堆空间中无指向
* b.又把 integerList 赋值给了 integerList1 , integerList1 为 null
* c.add 方法中对 integerList 重新初始化,生成堆空间,并添加内容
* d.主方法将 test 对象的地址给了 add() 方法中的 test 形参,形参的修改影响主方法中的 test 对象
* e.test.getIntegerList() 取到的是 add() 方法中的初始化后的对象信息
* 问题反思
* 1.因为方案设计时只考虑到了主方法中的属性一定非空的场景,那么add方法与主方法中的test对象均指向同一个堆空间
* 2.墨菲定律:如果可能出错就一定会出错;考虑为题要全面,如果空了该如何处理?
* 3.需要重点注意的场景:形参传递/数据拷贝/数值校验
* @param args
*/
public static void main(String[] args) {
Test test = new Test();
// List<Integer> integerList = test.getIntegerList();
// if(null == integerList){
// integerList = new ArrayList<>();
// test.setIntegerList(integerList);
// }
List<Integer> integerList1 = test.getIntegerList();
add(test);
List<Integer> integerList2 = test.getIntegerList();
System.out.println(integerList1);
System.out.println(integerList2);
// for (Integer integer : integerList1) {
// System.out.println(integer);
// }
}
private static void add(Test test){
List<Integer> integerList = test.getIntegerList();
if(null == integerList){
integerList = new ArrayList<>();
test.setIntegerList(integerList);
}
integerList.add(2);
}
} 来源:http://www./content-4-185301.html
|