00:00
那讲完了,我们上面提到了系统给大家提供好的引导类,扩展类,系统类,或者叫应用程序类加载器之外呢,咱们呃再来谈一谈,叫用户自定义的擂台加载器,那首先说呢,这块内容咱们不会展开讲的太多,具体的内容呢,咱们放到呃这个。咱们的下一篇哈,咱们现在讲的叫内存与垃圾回收品,咱们放到下一篇叫自检码和类的加载篇,咱们再去讲具体的,比如用户自定义一个类的加载器该怎么去做啊,那这块呢,咱们主要呢想说明两个问题啊,第一个呢,就是在什么时候咱们会去这个自定义类的加载器啊,这是第一个问题,第二个问题呢,就是简单的,如果要是定一个类的加载器的话呢,它的简单步骤是什么啊,是这样的一个情况啊好,那首先咱们来看这个正常来讲呢,在日常的开发当中啊,咱们这个类的加载,咱使用上面提供好的三类类的加载器啊,配合着去使用就可以了,说在一些必要的场景的时候,我们才会去自定义类的载器。啊,所以很多同学呢,可能在这个真正在企业中去开发,呃,具体一些场景之前的话呢,可能都没有接触过自定义类加载器啊,当然有些同学呢,是接触过了啊,那在什么下呢,场景下呢,我们才需要诶自定义类的加载器呢,呃,我这儿呢是罗列出来了四种情况。
01:18
啊,那凡是自定义过的,你看是不是有哪些跟你的需求是一样的啊,那第一个呢,这里提到叫隔离加载类。哎,隔离加载类什么意思呢?呃,就是咱们在某些框架当中啊,需要使用这个中间键,那中间键呢,跟这个应用呢,它们之间的模块呢,是隔离的啊,那隔离的话呢,我们就需要把这个类加载到不同的这个环境当中啊,比如说确保咱们应用当中你用的这个框架是吧,应用的这个炸包跟这个中间键使用这个炸包呢,它们是不冲突的啊,这叫隔离加载类。啊,说的可能还有点不太具体啊呃主要的需求呢,是由于比如说咱们这个中间件呢,都有自己呃依赖的大包,然后在同一个功能里边呢,咱们如果引入多个框架的话呢,呃有可能会出现比如说某些类呢,路径一样啊,类名也相同,那在这种情况下呢,就会出现呃这个类的冲突了,那那既然出现冲突呢,我们就需要做一个呃类的仲裁。
02:17
啊,那像主流的这个容器类这个框架呢,他们都会自定义这个类的加载器,然后实现呢,不同的这个中间件之间呢,它们是隔离的啊,避免这个类的冲突啊,这就提到就是隔离加载类啊这个问题,然后下个呢,我们叫呃修改类的加载方式啊,这个咱们说呢,在整个类的加载过程当中,这个boottrap呢,是一定要使用的啊,因为它一定会加载呃系统需要的一些核心的API,那至于说除了boottrap之外的其他的类的加载器呢,其实也不是说是必须的了,咱们可以根据在实际情况当中,哎,我具体要用的时候,我们再诶这个引入啊,所以呢,咱们可以使用这种方呃这个修改类加载器的就是使用自定义类加载器啊,可以在你需要的时候呢,进行一个动态的加载啊,体现的就是这样的一方面啊。
03:06
然后第三个呢,叫做扩展加载源,诶扩展加载源那除了我们前面提到了加载的类可以,呃,比如说有本地的物理磁盘呀,通过网络中啊,通过JA包中啊等等去加载之外呢,咱们还可以考虑像比如说数据库当中啊,甚至说这个电视机的机顶盒呀等等,哎,我们去加载这个自建码文件的来源,所以通过自定义类加载器呢,可以来扩展加载源啊,是这样问题。然后下一个啊,也是比较重要的一个方面啊,叫防止源码泄露啊,防止源码泄露,咱们说这个Java代码呢,实际上是很容易被编译和篡改的啊,你有了这个这个这个自己码文件以后呢,甚至我们你要没有这个反编译的一些手段的话呢,很容易呢,就被反编译了啊,容易被篡改,所以呢,我们为了防止被这个编译和篡改呢,咱们可以对这个这几码文件呢进行一个加密。啊,可以加密,那加密完以后呢,你自己肯定还要运行啊,那你自己在运行的时候,把它在还原成内存中的这个类去执行的时候呢,我们需要解密,那这时候呢,我们可以去自定义类的加载器去实现这样的一个呃解密操作啊,是这样的一个情况啊这呢就是我们说在什么样的场景下呢,会用到呃自定义这个类的加载器。
04:20
行,然后呢,咱们也简单来看一下哈,看一下就是如果我们要是自定义类的加载器的话呢,简单的一个步骤是什么样子的,大家应该也有一个,呃,简单印象就行,具体细节呢,咱们放到这个,哎,下一个篇章中再说,那咱们说要是自己来定义的话呢,这个把这字体好像不太大小一样啊。咱们要自己来定义的话呢,可以去继承这个class loader就行了,前面咱们也提到过,像扩展类这个像系统类,他们也是继承于class so,咱们也直接继承class so就行啊,然后来定义咱们这个自己的这个类加载器,然后这块呢,又下边有个迭代啊,然后在1.2之前呢,咱们要是继承class的话呢,大家需要去重写一个方法叫做load class。
05:06
啊是load class这个方法,然后实现你自定义的这个雷德加载器那1.2之后呢,咱就不用再去写这个load class了啊有点复杂了,呃,就是你需要指定的结构非常多啊,咱们呢,可以去重写另外的一个叫做find class这样的一个方法。诶,把你自定义的这个逻辑呢,就写在这个诶find的class当中,诶我这儿呢,也简单的写了一个例子啊,这个大家简单体会一下就行,你看这时候呢,我还是让他去继承一叫class loader,哎,此时呢,咱们就不需要再去重写刚才提到这个方法叫做哎load class了,咱们去重写这叫find class,哎,这个方法调用完以后呢,就能返回一个具体的呃,内存层面大的class的实例了,啊是这样子啊,下边有个具体的一个测试是吧?呃,那么我们在重写这个方法的过程当中,首先你需要考虑是根据指定的这个路径啊,诶,你把它以二进制流的方式呢,读到内存里边,形成一个字节数组。
06:02
哎,形成个字节数组,我这呢又重新定了个方法,诶,Get class,诶from custom custom pass,就是根据你给的路径,就像是一个读取文件一样啊,诶我们把它读进来,那这里边儿这个细节呢,我就不写了,以二进制流的方式呢,来读进来啊,那这时候大家注意,如果说呢,咱们体现了这一点的话啊,如果你本身这个呃,路径对应的这个自行码文件是一个加密的操作的话呢,那我们在这个读进来的时候呢,需要进行解密啊,我们在这说明啊。说如果,呃,指定路径的字节。妈。呃,文件啊,进行了加密。啊,则需要在此方法中呃进行解密操作。哎,解密完以后呢,让它还原成内存中的这个字节数组,然后呢,我们根据这个字节数组,如果它要不是一个呃,Now的话呢,我们再调用一个叫做诶DeFine class这样一个方法,那这呢,我们会看到这个fun class跟这个DeFine class它俩呢是需要这个配合使用的啊,这要注意一下,行这呢就是我简单的写了一个我们自定义的克拉搜的一个模型啊,一个大概的一个框啊,大家有这样个印象就行啊,然后再看下边。
07:25
所以啊,如果你要是自自定义这个类加载器,没有特殊复杂的这个需求的话呢,诶就没有必要再去这个继承这个class so了,你可以继承这个class so的它的一个子类叫做呃,URL class load啊避免呢,咱去重写这个find class,呃,以及呢,获取这个子解码流的这个方式了,那这样我们还是自己来获取这个流的方式了,呃,就是你要是没有特别复杂需求,只想体会一下这个,呃这个比如说从不同的场景下去加载,也没有说所谓的这个解密这样的一个需求的话呢,你就可以去继承ul class so就行啊那关于这个用户自定义的类加载器,大家呢,如果想对它进行了解的话呢,诶不需要落到这个具体写的层面上来说,诶你只需要呢,关注这两个问题啊,就是重写的话呢,大概怎么去重写,然后呢,诶为什么要自定义类加载器,诶就可以了。
我来说两句