上一篇我们讲到了ClosureCleaner的clean函数,这一篇我们继续往下分析,在clean函数中又调用了另外一个clean函数clean(func, level, checkSerializable, Collections.newSetFromMap(new IdentityHashMap<>()));代码如下:
private static void clean(Object func, ExecutionConfig.ClosureCleanerLevel level, boolean checkSerializable, Set<Object> visited) {
if (func == null) {
return;
}
//将func保存起来
if (!visited.add(func)) {
return;
}
//获取Object的Class对象
final Class<?> cls = func.getClass();
/*判断是否为基础类型还是包装类型,所谓基础类型就是int、float、long等这种非类对象类型
包装类型就是基础类型对应的Integer、Float、Long等类对象类型。
由于基础类型或者非基础类型
*/
if (ClassUtils.isPrimitiveOrWrapper(cls)) {
return;
}
//通过反射判断cls中是否有序列化函数writeReplace、writeObject,关于这两个函数的使用可以自己搜索一下,这里不详解
if (usesCustomSerialization(cls)) {
return;
}
// First find the field name of the "this$0" field, this can
// be "this$x" depending on the nesting
boolean closureAccessed = false;
//开始遍历cls中的所有成员变量
for (Field f: cls.getDeclaredFields()) {
//这部分代码我们下面详细讲解一下
if (f.getName().startsWith("this$")) {
// found a closure referencing field - now try to clean
closureAccessed |= cleanThis0(func, cls, f.getName());
} else {
Object fieldObject;
try {
//将该变量设置为可访问
f.setAccessible(true);
//获取该变量类对象