1. 程式人生 > >android檢測apk及dex方法數

android檢測apk及dex方法數

原文:http://www.jianshu.com/p/366b3ae72be6

隨著專案越來越大,android應用不得不面對64k方法數限制的問題,說真的,這個問題很頭疼,雖然網上已經有了多種解決方案,multidex,dynamicApk,程式碼混淆,業務邏輯用c實現然後用jni呼叫等等,dynamicApk需要工程模組化,高度解耦,修改量極大;程式碼混淆,已經做了,治標不治本;業務邏輯用c實現然後用jni呼叫,技術不到家是一種,各種依賴包的新增才是方法數爆棚的罪魁禍首,作用不大;multidex,雖然解了燃眉之急,但仍感到憂心忡忡,不是長久之計,還有各種坑等著你跳。

問題預防,檢測方法數

雖然目前還沒有一勞永逸的方案,只能走一步算一步,避免使用一些方法數較多的庫,時時刻刻意識到這問題,讓它慢一點到來,做我們能做的事,哦彌陀佛。

使用dexcount-gradle-plugin 計算apk方法數

用法
在app/build.gradle新增

buildscript {
    repositories {
        mavenCentral() // or jcenter()
    }

    dependencies {
        classpath 'com.getkeepsafe.dexcount:dexcount-gradle-plugin:0.3.0'
    }
}

apply plugin: 'com.getkeepsafe.dexcount'

簡單輸出

> ./gradlew assembleDebug

...buildspam...
:app
:compileDebugSources :app:preDexDebug UP-TO-DATE :app:dexDebug :app:packageDebug :app:zipalignDebug :app:assembleDebug Total methods in MyApp-debug-5.3.14.apk: 56538 BUILD SUCCESSFUL Total time: 33.017 secs

使用dex-method-count計算單個dex方法數

解壓apk檔案可以看到classes.dex檔案,如果使用了multidex可能會看到多個classses.dex,classes2.dex等。
這裡使用了網上找的一個指令碼,很早之前看到的,找不到出處了,貼出來

printhex.ps1

<#
.SYNOPSIS
Outputs the number of methods in a dex file.

.PARAMETER Path
Specifies the path to a file. Wildcards are not permitted.

#>
param(
  [parameter(Position=0,Mandatory=$TRUE)]
    [String] $Path
)

if ( -not (test-path -literalpath $Path) ) {
  write-error "Path '$Path' not found." -category ObjectNotFound
  exit
}

$item = get-item -literalpath $Path -force
if ( -not ($? -and ($item -is [System.IO.FileInfo])) ) {
  write-error "'$Path' is not a file in the file system." -category InvalidType
  exit
}

if ( $item.Length -gt [UInt32]::MaxValue ) {
  write-error "'$Path' is too large." -category OpenError
  exit
}

$stream = [System.IO.File]::OpenRead($item.FullName)
$buffer = new-object Byte[] 2
$stream.Position = 88
$bytesread = $stream.Read($buffer, 0, 2)
$output = $buffer[0..1] 
#("{1:X2} {0:X2}") -f $output
$outputdec = $buffer[1]*256 + $buffer[0]
"Number of methods is " + $outputdec
$stream.Close()

dex-method-count.bat

@ECHO OFF

IF "%1"=="" GOTO MissingFileNameError

IF EXIST "%1" (GOTO ContinueProcessing) ELSE (GOTO FileDoesntExist)



:ContinueProcessing

set FileNameToProcess=%1

set FileNameForDx=%~n1.dex

IF "%~x1"==".dex" GOTO ProcessWithPowerShell



REM preprocess Jar with dx

IF "%~x1"==".jar" (

    ECHO Processing Jar %FileNameToProcess% with DX!

    CALL dx --dex --output=%FileNameForDx% %FileNameToProcess%

    set FileNameToProcess=%FileNameForDx%

    IF ERRORLEVEL 1 GOTO DxProcessingError

)



:ProcessWithPowerShell

ECHO Counting methods in DEX file %FileNameToProcess%

CALL powershell -noexit -executionpolicy bypass "& ".\printhex.ps1" %FileNameToProcess%

GOTO End



:MissingFileNameError

@ECHO Missing filename for processing

GOTO End



:DxProcessingError

@ECHO Error processing file %1% with dx!

GOTO End



:FileDoesntExist

@ECHO File %1% doesn't exist!

GOTO End



:End

用法:
將上面兩個檔案拷貝到電腦(windows),檔名字和字尾都不要變,且放在同一個目錄下,需要檢測的dex檔案也放在同一級目錄,就像這樣


QQ截圖20151116174811.png


開啟命令列並切到當前目錄下,執行命令

dex-method-count.bat classes.dex

執行結果:Number of methods is 64595


QQ截圖20151116175052.png

計算開源庫方法數的網站



文/dongjunkun(簡書作者)
原文連結:http://www.jianshu.com/p/366b3ae72be6

著作權歸作者所有,轉載請聯絡作者獲得授權,並標註“簡書作者”。