Android 耗电总结---概览
引言
之前和业务线进行耗电优化,业务线是 IoT 设备,故对耗电的要求很高,多一次闹钟唤醒,多一次网络请求都无所遁形。再加上之前适配 Android O 对 background Service 的限制,感觉耗电问题的知识过于零散,于是就想总结一下,本文的主要的目标是想让大家有一个总体的印象,了解 Android 是如何计算耗电,后面会陆续对 Android 的耗电进行总结。
耗电计算
分析耗电之前,我们首先要明白 Android 是如何统计耗电的。耗电的统计在类
frameworks/core/java/com/android/internal/os/BatteryStatsHelper.java
硬件耗电
一说到耗电,我们就会想到初中的物理公式
P = U * I
W = P * t
其实 Android 设备的功率并没有我们想象的那么复杂,由于 Android 设备电压恒定,只需要定义每种硬件设备在运行时的电流即可计算一段时间内每种硬件的功耗。Android 将每种硬件在运行时的电流保存以下文件中
frameworks/core/res/res/xml/power_profile.xml
<device name="Android">
......
<item name="wifi.on">0.1</item><!-- ~3mA -->
<item name="wifi.active">0.1</item><!-- WIFI data transfer, ~200mA -->
<item name="wifi.scan">0.1</item><!-- WIFI network scanning, ~100mA -->
.......
</device>
可以看到以上的配置文件中,定义了 Wi-Fi 模块在 on active 以及 scan 时不同的电流数值。通过这些预定义的数据再加上运行的时间,就可以知道这段时间内不同硬件的耗电情况。
以上就是 Android 统计硬件耗电的方法,总结起来就是先定义好不同硬件在不同状态下的功率,然后根据时间计算这段时间内硬件的耗电,感兴趣的同学可以去仔细分析一下 BatteryStatHelper 类中 processMiscUsage 函数。
软件耗电
app 耗电的计算实际上就是计算 app 在运行期间使用手机硬件所产生的能耗。可以看下计算的逻辑。
private void processAppUsage(SparseArray<UserHandle> asUsers) {
......
for(int iu = 0; iu < NU; iu++) {
// 统计每一个应用的耗电信息
final Uid u = uidStats.valueAt(iu);
final BatterySipper app = new BatterySipper(BatterySipper.DrainType.APP, u, 0);
// CPU
mCpuPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// WakeLock
mWakelockPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// 移动网络
mMobileRadioPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs,
mStatsType);
// wifi
mWifiPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// 蓝牙
mBluetoothPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs,
mStatsType);
// 传感器
mSensorPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// 相机
mCameraPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// 闪光灯
mFlashlightPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs,
mStatsType);
// 多媒体
mMediaPowerCalculator.calculateApp(app, u, mRawRealtimeUs, mRawUptimeUs, mStatsType);
// 统计总的耗电
final double totalPower = app.sumPower();
......
}
......
}
可以看下 sumPower( ) 函数的实现
public double sumPower() {
totalPowerMah = usagePowerMah + wifiPowerMah + gpsPowerMah + cpuPowerMah +
sensorPowerMah + mobileRadioPowerMah + wakeLockPowerMah + cameraPowerMah +
flashlightPowerMah + bluetoothPowerMah + audioPowerMah + videoPowerMah;
......
return totalPowerMah;
}
总结
本文带着大家了解了 Android 耗电计算的逻辑,后面的文章将会带着大家逐步去分析 Android 的 App 耗电。
推荐阅读
下一篇: Android逐帧动画——让图片动起来