Android在apk文件dex文件是java编译出来.class次打包,当然在打包之前会利用自己的协议做一些数据处理,比如优化函数表和变量表。在java程序中是使用classloader来载入这些编译生成的.class文件,然而在android程序中是通过DexClassLoader来装载这些文件的.这里我们就能够通过DexClassLoader在程序A里面动态装载程序B中的类,而且来调用B程序中的方法.

1.首先先建立一个普通的Androidproject,在这个project中定义一个叫做plugin的类,类中实现一个简单的方法,例如以下所看到的:

<span style="font-size:14px;">public class PluginClass {
private static String TAG = PluginClass.class.getSimpleName();
public PluginClass(){
Log.i(TAG, "initialized");
}
public void invoke(String s){
Log.i(TAG, s);
}
}</span>

2.将这个Androidproject执行到安卓设备其中去

3.再又一次建立一个Androidproject,当中定义一个叫做host的类,在这个类中实现DexClassLoader动态载入第一个project中的plugin类,例如以下所看到的:

<span style="font-size:14px;">public class HostClass {
private static String TAG = HostClass.class.getSimpleName();
private Context mContext = null;
public HostClass(Context contect){
mContext = contect;
}
public void useDexClassLoader(){
Intent intent = new Intent();
intent.setPackage("com.example.plugin");
PackageManager pm = mContext.getPackageManager();
final List<ResolveInfo> plugins = pm.queryIntentActivities(intent,0);
if(plugins.size() <= 0){
Log.i(TAG, "resolve info size is:" + plugins.size());
return;
}
ResolveInfo resolveInfo = plugins.get(0);
ActivityInfo activityInfo = resolveInfo.activityInfo; String div = System.getProperty("path.separator");
String packageName = activityInfo.packageName;
String dexPath = activityInfo.applicationInfo.sourceDir;
//目标类所在的apk或者jar的路径。class loader会通过这个路径来载入目标类文件
String dexOutputDir = mContext.getApplicationInfo().dataDir;
//因为dex文件是包括在apk或者jar文件里的,所以在载入class之前就须要先将dex文件解压出来,dexOutputDir为解压路径
String libPath = activityInfo.applicationInfo.nativeLibraryDir;
//目标类可能使用的c或者c++的库文件的存放路径 Log.i(TAG, "div:" + div + " " +
"packageName:" + packageName + " " +
"dexPath:" + dexPath + " " +
"dexOutputDir:" + dexOutputDir + " " +
"libPath:" + libPath); DexClassLoader dcLoader = new DexClassLoader(dexPath,dexOutputDir,libPath,this.getClass().getClassLoader());
try {
Class<?> clazz = dcLoader.loadClass(packageName + ".PluginClass");
Object obj = clazz.newInstance();
Class[] param = new Class[1];
param[0] = String.class;
Method action = clazz.getMethod("invoke", param);
action.invoke(obj, "test this function");
} catch (ClassNotFoundException e) {
Log.i(TAG, "ClassNotFoundException");
} catch (InstantiationException e) {
Log.i(TAG, "InstantiationException");
} catch (IllegalAccessException e) {
Log.i(TAG, "IllegalAccessException");
} catch (NoSuchMethodException e) {
Log.i(TAG, "NoSuchMethodException");
} catch (IllegalArgumentException e) {
Log.i(TAG, "IllegalArgumentException");
} catch (InvocationTargetException e) {
Log.i(TAG, "InvocationTargetException");
}
}
}</span>

4.执行第二个project之后查看log就会发现host通过DexClassLoader载入了pluginclass类,并成功调用了plugin中的方法

<span style="font-size:14px;">I/HostClass( 8341): div::   packageName:com.example.plugin   dexPath:/data/app/com.example.plugin-1.apk   dexOutputDir:/data/data/com.example.host   libPath:/data/app-lib/com.example.plugin-1
D/dalvikvm( 8341): DexOpt: --- BEGIN 'com.example.plugin-1.apk' (bootstrap=0) ---
D/dalvikvm( 8341): DexOpt: --- END 'com.example.plugin-1.apk' (success) ---
D/dalvikvm( 8341): DEX prep '/data/app/com.example.plugin-1.apk': unzip in 39ms, rewrite 723ms
I/PluginClass( 8341): initialized
I/PluginClass( 8341): test this function
D/libEGL ( 8341): loaded /system/lib/egl/libEGL_mali.so
D/libEGL ( 8341): loaded /system/lib/egl/libGLESv1_CM_mali.so
D/libEGL ( 8341): loaded /system/lib/egl/libGLESv2_mali.so
D/OpenGLRenderer( 8341): Enabling debug mode 0
I/HostClass( 8341): div:: packageName:com.example.plugin dexPath:/data/app/com.example.plugin-1.apk dexOutputDir:/data/data/com.example.host libPath:/data/app-lib/com.example.plugin-1
I/PluginClass( 8341): initialized
I/PluginClass( 8341): test this function</span>

版权声明:本文博客原创文章。博客,未经同意,不得转载。

Android 使用DexClassLoader要执行其他apk方法的更多相关文章

  1. android 实现返回键执行home键方法

    在公司的产品开发,中老板很是执着于,不要看到启动界面,但是又不想去掉启动界面. so 实现返回键执行home键方法. public boolean onKeyDown(int keyCode, Key ...

  2. Android插件化开发---执行未安装apk中的Service

    欢迎各位增加我的Android开发群[257053751​] 假设你还不知道什么叫插件化开发.那么你应该先读一读之前写的这篇博客:Android插件化开发,初入殿堂 上一篇博客主要从总体角度分析了一下 ...

  3. Android预置Apk方法

    这一套8.0过时了 需要修改pms代码 否则apk会被pms删除掉 因为工作需要,经常要开发和合入系统App,所以在此开篇作为收集和记录Android合入系统应用的方法,以备日后查阅. 一.预置apk ...

  4. android无后缀二进制执行文件替代apk实现程序功能

    韩梦飞沙  韩亚飞  313134555@qq.com  yue31313  han_meng_fei_sha android无后缀二进制执行文件替代apk实现程序功能 实现将data/Android ...

  5. Android常用异步任务执行方法

    Handler原理及基本概念 Message 意为消息,发送到Handler进行处理的对象,携带描述信息和任意数据. MessageQueue 意为消息队列,Message的集合. Looper 有着 ...

  6. 【Android】Android动态加载Jar、APK的实现

    本文介绍Android中动态加载Jar.APK的实现.而主要用到的就是DexClassLoader这个类.大家都知道Android和普通的Java虚拟机有差别,它只能加载经过处理的dex文件.而加载这 ...

  7. Android线程间通信更新UI的方法(重点分析EventBus)

    Android的UI更新只能在UI线程中,即主线程.子线程中如果要进行UI更新,都是要通知主线程来进行. 几种实现方式总结如下,欢迎补充. 1.runOnUiThread() 子线程中持有当前Acti ...

  8. Android程序的签名保护及绕过方法

    随着Android 市场的扩大,各类盗版.破解.打包党纷纷涌现,其使用的手法无非是apk _> smali ->修改代码 ->重打包签名,为对抗此类技术,广大程序员挖掘了Androi ...

  9. 【Android】getActionBar()为null的解决方法总结

    前言 在使用 ActionBar的时候,有时候会爆出空指针异常,这是由于应用没有获取到 ActionBar 导致的,而导致应用没有获取到 ActionBar 的原因比較多.所以我们以下就来总结一下 A ...

随机推荐

  1. C# Out和Ref区别

    rel是有进有出,out是只出不进 ref 要求参数在传递给函数前要初始化,out则不需要

  2. android学习经常使用的数据文件夹

    android工程实践 1.仿360一键清理实现(一) "一键清理"是一个桌面图标,点击图标后,显示一个视图.进行清理动画.之后显示清理了几个进程,释放了多少M内存.点击" ...

  3. JAVA基础编程50题(10-12题)具体解释

    一.描写叙述 1.一球从m米高度自由落下.每次落地后反跳回原高度的一半:再落下,求它在 第n次落地时.共经过多少米?第10次反弹多高? 2.有1.2.3.4个数字.能组成多少个互不同样且无反复数字的三 ...

  4. 引用第三方框架 不支持ARC

    我们会常常遇到一个问题就是引用第三方框架之后发现不支持内存的自己主动处理(ARC) 我们须要这样来操作: watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvdT ...

  5. 同ListView该接口无法通过手势滑动左右切换界面问题解决方法

    同ListView该接口无法通过手势滑动左右切换界面问题解决方法 问题描写叙述: 在做OnGestureListener滑动切换窗体的时候,会遇到这种问题.就是当界面中含有ListView的时候.On ...

  6. vmWare虚拟机下ubuntu配置代理上网

    最终用上了linux,windows下用vmWare安装虚拟机,挂ubuntu 14.04,,认为非常不习惯,非常难侍候. 而且遇到的客观困难还不少,这两天着实费了不少功夫.主要是上班这里上网要配置代 ...

  7. Android之Handler的postDelayed()使用方法

    这是一种创建多线程信息功能 用法: 1,首先创建一个Handler物 Handler handler=new Handler(); 2.然后创建一个Runnable物 Runnable runnabl ...

  8. MVC—WebAPI(调用、授权)

    ASP.NET MVC—WebAPI(调用.授权)   本系列目录:ASP.NET MVC4入门到精通系列目录汇总 微软有了Webservice和WCF,为什么还要有WebAPI? 用过WCF的人应该 ...

  9. 深入理解Android中ViewGroup

    文章目录   [隐藏] 一.ViewGroup是什么? 二.ViewGroup这个容器 2.1 添加View的算法 2.1.1 我们先来分析addViewInner方法: 2.1.2 addInArr ...

  10. UML造型——使用EA时序图工具的开发实践和经验

    Enterprise Architect watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQveGlhb3l3NzE=/font/5a6L5L2T/fontsiz ...