首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Android-使用DexClassLoader加载apk文件

Android-使用DexClassLoader加载apk文件
EN

Stack Overflow用户
提问于 2010-05-25 17:02:02
回答 3查看 18.6K关注 0票数 22

我遇到了一点麻烦。任何帮助都将不胜感激。我有一个应用程序,我想使用DexClassLoader来加载另一个apk文件。

下面是我的代码:

代码语言:javascript
复制
DexClassLoader dLoader = new DexClassLoader("/sdcard/download/test.apk","/sdcard/download",null,ClassLoader.getSystemClassLoader().getParent());
Class calledClass = dLoader.loadClass("com.test.classname");
Intent it=new Intent(this, calledClass);
it.setClassName("com.test", "com.test.classname");
startActivity(it);

现在我已经安装了test.apk,所以当我运行上面的代码时,它工作得很好,并启动了应用程序。但是,我希望能够在没有安装test.apk的情况下运行它(因为这会破坏应用程序的全部功能)。所以我卸载了它,当我再次运行我的应用程序时,我得到了这个错误:

代码语言:javascript
复制
android.content.ActivityNotFoundException: Unable to find explicit
activity class {com.test/com.test.classname}; have you declared this
activity in your AndroidManifest.xml.

所以我有点迷惑了。此活动在我试图运行的apk的清单中声明。我无法在我的应用程序清单中声明它。有什么想法吗?

谢谢,克雷格

EN

回答 3

Stack Overflow用户

发布于 2010-10-26 16:56:11

尝试使用安卓的PathClassLoader

代码语言:javascript
复制
    String packagePath = "com.mypackage";
    String classPath = "com.mypackage.ExternalClass";

    String apkName = null;
    try {
        apkName = getPackageManager().getApplicationInfo(packagePath,0).sourceDir;
    } catch (PackageManager.NameNotFoundException e) {
        // catch this
    }

    // add path to apk that contains classes you wish to load
    String extraApkPath = apkName + ":/path/to/extraLib.apk" 

    PathClassLoader pathClassLoader = new dalvik.system.PathClassLoader(
            apkName,
            ClassLoader.getSystemClassLoader());

    try {
        Class<?> handler = Class.forName(classPath, true, pathClassLoader);
    } catch (ClassNotFoundException e) {
        // catch this
    }
票数 11
EN

Stack Overflow用户

发布于 2014-08-17 05:17:26

虽然这个问题很老,但我还是会回答的,因为我有点费力地为你的相同问题找到了一个明确的答案。首先,我想强调的是,您问题中的一个明确要求是从尚未安装在设备上的.apk加载一个类。因此,使用getPackageManager()调用包管理器并为其提供包路径显然会导致NameNotFoundException,因为设备上没有安装包含该包的.apk

因此,从设备上未安装的 .apk 文件加载类的方法是使用DexClassLoader,如下所示:

1-确保您的SD卡上的某个目录中有.apk文件。我已经在我的SD卡的下载文件夹中找到了Offloadme.apk

2-在您的AndroidManifest.xml中添加读取权限,以允许您的应用程序从清单中读取。

代码语言:javascript
复制
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>

3-使用以下定义来定义.apk的路径、apk内的类名以及要调用的类中的方法名:

代码语言:javascript
复制
final String apkFile =Environment.getExternalStorageDirectory().getAbsolutePath()+"/Download/Offloadme.apk";
String className = "com.khaledalanezi.offloadme.SimpleCalculator";
String methodToInvoke = "add"; 

4-使用DexClassLoader加载.apk,并使用反射调用SimpleCalculator类中的add方法,如下所示:

代码语言:javascript
复制
    final File optimizedDexOutputPath = getDir("outdex", 0);

    DexClassLoader dLoader = new DexClassLoader(apkFile,optimizedDexOutputPath.getAbsolutePath(),
            null,ClassLoader.getSystemClassLoader().getParent());

    try {
        Class<?> loadedClass = dLoader.loadClass(className);
        Object obj = (Object)loadedClass.newInstance();
        int x =5;
        int y=6;
        Method m = loadedClass.getMethod(methodToInvoke, int.class, int.class);
        int z = (Integer) m.invoke(obj, y, x);              
        System.out.println("The sum of "+x+" and "+"y="+z);

    } catch (ClassNotFoundException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (InstantiationException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (IllegalAccessException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (NoSuchMethodException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (IllegalArgumentException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (InvocationTargetException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

请注意,在我的简单示例中,我使用从我的SD卡上存储的Offloadme.apk文件加载的SimpleCalculator类中可用的add方法将两个数字相加,并且我能够打印正确的答案11。

票数 8
EN

Stack Overflow用户

发布于 2010-09-16 07:31:35

你不能这么做。即使你能够从外部文件访问类,Android仍然不知道它们。而且你不是直接运行活动,而是通过请求Android来运行它们,所以它们必须注册/安装到系统中。

票数 -6
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/2903260

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档