繁体   English   中英

正确使用Classloader(特别是在Android中)

[英]Correct use of Classloader (especially in Android)

我阅读了一些关于类加载器的文档,但我仍然不确定它们的位置和原因。 Android API说:

从存储库加载类和资源。 在运行时安装一个或多个类加载器。 只要运行时系统需要一个尚未在内存中可用的特定类,就会查询这些内容。

因此,如果我理解这是正确的,那么可以有许多负责加载新类的classlaoders。 但系统如何决定使用哪个? 在哪种情况下,开发人员应该实例化一个新的类加载器?

在Intent的Android API中有一种方法

public void  setExtrasClassLoader  (ClassLoader  loader)

描述说:

设置从此Intent的extras中解组任何Parcelable值时将使用的ClassLoader。

那么我可以定义一个特殊的类加载器,以便我可以使用未在接收活动中定义的Intent传递对象吗? 一个例子:

如果位于项目A(在Eclipse中)的活动A使用Intent对象的putExtra定义了我想要发送到项目B中的活动B的对象。 如果未定义通过Intent发送的此对象(项目B中的源代码),则存在NoClassDefFoundException。 那么我可以使用方法setExtraClassloader来避免这种异常吗? 如果是,我如何决定我必须通过哪个类加载器对象? 我如何正确实例化它?

我阅读了一些关于类加载器的文档,但我仍然不确定它们的位置和原因。

一般来说,您不需要触摸类加载器系统。

在哪种情况下,开发人员应该实例化一个新的类加载器?

经过大约十年的Java编程经验。 :-)

如果位于项目A(在Eclipse中)的活动A使用Intent对象的putExtra定义了我想要发送到项目B中的活动B的对象。 如果未定义通过Intent发送的此对象(项目B中的源代码),则存在NoClassDefFoundException。 那么我可以使用方法setExtraClassloader来避免这种异常吗?

不,因为项目A和项目B无法共享代码。 把你需要的课程放在两个项目中。 或者使用带有AIDL的远程服务接口,而不是Intents和extras。 或者不要使用自定义类,而是将对象视为数据结构(例如,使用简单的Strings HashMap或其他东西)。

这是一个迟到的答案,但希望它会帮助其他人。

通常,类加载器用于在运行时加载可执行的Java代码。 一个很好的例子就是从互联网上下载的插件。 您可以从类文件中获取二进制数据,加载它,并根据需要调用其中的函数。 当然,您需要使用调用程序已知的接口或抽象类,以便它知道如何使用该类。

当典型庄园中无法访问二进制类数据时,将使用自定义类加载器。 例如,如果您的蓝牙设备包含带有实现接口的代码的类文件,则需要编写自定义类加载器以通过蓝牙接口加载类数据。

您可能想要编写自定义类加载器的另一个原因是,如果要更改加载的类访问其他类的方式。 您可以限制加载的类可以访问哪些内部类,甚至可以编写自己的类,从而更改内部类的行为。 例如,如果加载的类使用Java.io.File类,则可能需要强制它使用内部类以不同的方式访问文件。

简而言之,当您编写自定义类加载器时,您可以更改类的加载方式,以及加载的类如何加载所有其他类。

ClassLoaders并不是那么难理解,至少在库存Java领域是这样。 (我可以在90分钟内教你ClassLoader系统 - 我在No Fluff Just Stuff节目中一直这样做。)这就是说,大多数时候你不需要创建自定义ClassLoader - 如果你想要的话在路上使用字节码的futz,java.lang.instrument是你的朋友。 如果要从URL加载代码,请查看java.net.URLClassLoader。 在这两者之间,对自定义ClassLoader的需求完全是零。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM