Android-主dex超过限制的解决方案-Too manyclasses in --main-dex-list, main dex capacity exceeded

来源:互联网 发布:绝对计划 知乎 编辑:程序博客网 时间:2024/06/06 16:54

问题描述:

由于工程不断的版本迭代,工程中的类太多,虽然经过了分多个dex的处理(分多个dex的方法我就不说了,百度一大堆),在不断加入更多的类之后,主dex的类超过了限制。


具体报错:

com.android.dex.DexException: Too manyclasses in --main-dex-list, main dex capacity exceeded

         atcom.android.dx.command.dexer.Main.processAllFiles(Main.java:546)

         atcom.android.dx.command.dexer.Main.run(Main.java:275)

         atcom.android.dx.command.dexer.Main.runMultiDex(Main.java:366)

         atcom.android.dx.command.dexer.Main.main(Main.java:245)

         atcom.android.dx.command.Main.main(Main.java:106)

Error:Execution failed for task':12580:dexDebug'.

>com.android.ide.common.process.ProcessException:org.gradle.process.internal.ExecException: Process 'command 'C:\ProgramFiles\Java\jdk1.8.0_45\bin\java.exe'' finished with non-zero exit value 2


就不解释产生这个的原因了,主要我还解释不了,哈哈,直接进入解决方案。


解决方案步骤:

1.     修改app的build.gradle中gradle插件的版本:

修改为classpath 'com.android.tools.build:gradle:2.0.0' 


2.     修改gradle-wrapper.properties文件中gradle的版本:

修改为gradle-2.10-all.zip


3.     在module的build.gradle文件中添加下面代码:

import java.lang.reflect.Array

import java.lang.reflect.Field

 

defpatchKeepSpecs() {

    def clazz =Class.forName("com.android.build.gradle.internal.tasks.multidex.CreateManifestKeepList")

    def keepSpecsField =clazz.getDeclaredField("KEEP_SPECS")

    keepSpecsField.setAccessible(true)

    def keepSpecs = (Map)keepSpecsField.get(null)

 

    println "\nKEEP_SPECS **before**patch:"

    for (def item : keepSpecs) {

        if (item) {

            println item

        }

    }

    println ''

    excludeElement(keepSpecs,"activity")

 

    println "\nKEEP_SPECS **after**patch:"

    for (def item : keepSpecs) {

        if (item) {

            println item

        }

    }

    println ''

}

 

defexcludeElement(keepSpecs, element) {

    Class mapClazz =Class.forName("com.google.common.collect.RegularImmutableMap")

    Field tableField = mapClazz.getDeclaredField("table")

    tableField.setAccessible(true)

    def table = tableField.get(keepSpecs)

 

    def index = getElementIndex(table, element)

    if (index == -1) {

        println "KEEP_SPECS (table): no'$element' found"

    } else {

       Array.set(table, index, null)

        println "KEEP_SPECS (table)patched: removed '$element' root"

    }

 

    def entriesField =mapClazz.getDeclaredField("entries")

    entriesField.setAccessible(true)

    def entries = entriesField.get(keepSpecs)

 

    index = getElementIndex(entries, element)

    if (index == -1) {

        println "KEEP_SPECS (entries): no'$element' found"

    } else {

        Array.set(entries, index, null)

        println "KEEP_SPECS (entries)patched: removed '$element' root"

    }

}

 

defgetElementIndex(container, element) {

    int length = Array.getLength(container)

    for (int i=0; i < length; ++i) {

        def entry = Array.get(container, i)

        if (entry != null) {

            if (element.equals(entry.getKey())){

                return i

            }

        }

    }

    return -1

}

 

 

patchKeepSpecs()


4.     重新编译运行即可。


本文参考文章:http://stackoverflow.com/questions/32721083/too-many-classes-in-main-dex-list-main-dex-capacity-exceeded
0 0
原创粉丝点击