Android应用性能优化

Android手机由于其本身的后台机制和硬件特点,性能上一直被诟病,所以软件开发者对软件本身的性能优化就显得尤为重要;本文将对Android开发过程中性能优化的各个方面做一个回顾与总结。

Cache优化

  • ListView缓存:

    • ListView中有一个回收器,Item滑出界面的时候View会回收到这里,需要显示新的Item的时候,就尽量重用回收器里面的View;每次在getView函数中inflate新的item之前会先判断回收器中是否有缓存的view,即判断convertView是否为null,是则inflate一个新的item View,否则重用回收器中的item。
    • 此外,ListView还使用静态的ViewHolder减少findViewById的次数
    • ListView中有getViewTypeCount()函数用于获取列表有几种布局类型,getItemViewType(int position)用于获取在position位置上的布局类型; 我们可以利用ViewType来给不同类型的item创建不同的View,这样可以利于ListView的回收
    • 对Item中图片进行适当压缩, 并进行异步加载;如果快速滑动,不加载图片;实现数据的分页加载
  • IO缓存:在文件和网络IO中使用具有缓存策略的输入流,BufferedInputStream替代InputStream,BufferedReader替代Reader,BufferedReader替代BufferedInputStream

  • data缓存(空间换时间):①缓存数据库的查询结果,比如缓存数据库表中的数据条数,这样就可以避免多次的select count查询 ②缓存磁盘文件中需要频繁访问的数据到内存中 ③缓存耗时计算的结果

Battery优化

  • cpu的使用率和使用频率将直接或间接的影响电量的分配和使用,cpu降频可以节约电量
  • service优化
    • service作为一个运行在主线程中的后台服务,应该尽量避免耗时动作,而应该尽量新开线程去处理耗时动作
      监听系统广播看service是否存活,否则kill掉;降低service优先级使得系统内存吃紧时会被自动kill掉

    • 使用Android提供的IntentService代替service,因为IntentService会在运行完成之后自动停止,而service需要手动调用stopService()才能停止运行

    • 定时执行任务的Alarm机制:Android的定时任务有两种实现方式,Timer类和Alarm机制;Timer不适合长期后台运行的定时任务。因为每种手机都会有自己的休眠策略,Android手机就会在长时间不操作的情况下自动让CPU进入到睡眠状态,这就有可能导致Timer中的定时任务无法正常运行。而Alarm机制则不存在这种情况,它具有唤醒CPU的功能,即可以保证每次需要执行定时任务的时候CPU能正常工作。然而从Android4.4之后,Alarm任务的触发时间将会变得不准确,有可能会延迟一段时间后任务才能得到执行。这不是bug,而是系统在耗电性方面进行的优化。系统会自动检测目前有多少Alarm任务存在,然后将触发时间将近的几个任务放在一起执行,这就可以大幅度的减少CPU被唤醒的次数,从而有效延长电池的使用时间

渲染层优化

  • Android 界面卡顿的原因?

    • UI线程中做耗时操作,比如进行网络请求,磁盘读取,位图修改,更新UI等耗时操作,从而导致UI线程卡顿
    • 布局Layout过于复杂,无法在16ms内完成渲染,或者嵌套层次过深
    • View过度绘制或者频繁的触发measure、layout,同一时间动画执行的次数过多,导致CPU或GPU负载过重
    • 冗余资源及逻辑等导致加载和执行缓慢
  • Android 界面卡顿怎么处理?

    • xml布局优化:尽量使用include、merge、ViewStub标签,尽量不存在冗余嵌套及过于复杂布局(譬如10层就会直接异常),例如使用RelativeLayout代替LinearLayout可以减少布局层次和复杂性,View的嵌套层次不能过深,尽量使用GONE替换INVISIBLE,使用weight后尽量将width和heigh设置为0dp,减少运算,Item存在非常复杂的嵌套时考虑使用自定义Item View来取代,减少measure与layout次数等。
    • ListView及Adapter优化;尽量复用getView方法中的相关View,不重复获取实例导致卡顿,列表尽量在滑动过程中不进行UI元素刷新等。
    • 背景和图片等内存分配优化;尽量减少不必要的背景设置,图片尽量压缩处理显示,尽量避免频繁内存抖动等问题出现;尽可能为不同分辨率创建资源,以减少不必要的硬件缩放
    • 自定义View等绘图与布局优化;尽量避免在draw、measure、layout中做过于耗时及耗内存操作,尤其是draw方法中,尽量减少draw、measure、layout等执行次数,避免过度渲染和绘制;减少不必要的inflate,尽量使用全局变量缓存View
    • 避免ANR,不要在UI线程中做耗时操作,譬如多次数据库操作等
  • Layout常用的标签

    • include标签:该标签可以用于将布局文件中的公共部分提取出来给其它布局文件复用,从而使得布局模块化,代码轻量化; 注意点: ①如果标签已经定义了id,而嵌入布局文件的root布局文件也定义了id,标签的id会覆盖掉嵌入布局文件root的id,如果include标签没有定义id则会使用嵌入文件root的id ②如果想使用标签覆盖嵌入布局root布局属性,必须同时覆盖layout_height和layout_width属性,否则会直接报编译时语法错误

    • viewstub标签:该标签与include一样用于引入布局模块,只是引入的布局默认不会扩张,既不会占用显示也不会占用位置,从而在解析layout时节省cpu和内存,只有通过调用setVisibility函数或者Inflate函数才会将其要装载的目标布局给加载出来,从而达到延迟加载的效果;例如条目详情、进度条标识或者未读消息等,这些情况如果在一开始初始化,虽然设置可见性View.GONE,但是在Inflate的时候View仍然会被Inflate,仍然会创建对象。

    • merge标签:该标签在layout中会被自动忽略,从而减少一层布局嵌套,其主要用处是当一个布局作为子布局被其他布局include时,使用merge当作该布局的顶节点来代替layout顶节点就可以减少一层嵌套

    • hierarchy viewer:该工具可以方便的查看Activity的布局,各个View的属性、measure、layout、draw的时间,如果耗时较多会用红色标记,否则显示绿色

网络优化

  • 异步请求网络数据,避免频繁请求数据(例如如果某个页面内请求过多,可以考虑做一定的请求合并),尽可能的减少网络请求次数和减小网络请求时间间隔

  • 网络应用传输中使用高效率的数据格式,譬如使用JSON代替XML,使用WebP代替其他图片格式,并对数据进行Gzip压缩数据,比如post请求的body和header内容

  • 及时缓存数据到内存/文件/数据库

  • 执行某些操作前尽量先进行网络状态判断,比如wifi传输数据比蜂窝数据更省电,所以尽量在wifi下进行数据的预加载

  • httpClient和httpUrlConnection对比:

    • httpClient是apache的开源实现,API数量多,非常稳定
    • httpUrlConnection是java自带的模块: ①可以直接支持GZIP压缩,而HttpClient虽然也支持GZIP,但要自己写代码处理 ②httpUrlConnection直接在系统层面做了缓存策略处理,加快重复请求的速度 ③API简单,体积较小,而且直接支持系统级连接池,即打开的连接不会直接关闭,在一段时间内所有程序可共用
    • HttpURLConnection在Android2.2之前有个重大Bug,调用close()函数会影响连接池,导致连接复用失效,需要关闭keepAlive;因此在2.2之前http请求都是用httpClient,2.2之后则是使用HttpURLConnection
    • 但是!!!现在!!!Android不再推荐这两种方式!二是直接使用OKHttp这种成熟方案!支持Android 2.3及其以上版本

数据结构优化

  • ArrayList和LinkedList的选择:ArrayList根据index取值更快,LinkedList更占内存、随机插入删除更快速、扩容效率更高

  • ArrayList、HashMap、LinkedHashMap、HashSet的选择:hash系列数据结构查询速度更优,ArrayList存储有序元素,HashMap为键值对数据结构,LinkedHashMap可以记住加入次序的hashMap,HashSet不允许重复元素

  • HashMap、WeakHashMap选择:WeakHashMap中元素可在适当时候被系统垃圾回收器自动回收,所以适合在内存紧张时使用

  • Collections.synchronizedMap和ConcurrentHashMap的选择:ConcurrentHashMap为细分锁,锁粒度更小,并发性能更优;Collections.synchronizedMap为对象锁,自己添加函数进行锁控制更方便

  • Android中性能更优的数据类型:如SparseArray、SparseBooleanArray、SparseIntArray、Pair;Sparse系列的数据结构是为key为int情况的特殊处理,采用二分查找及简单的数组存储,加上不需要泛型转换的开销,相对Map来说性能更优

内存优化

  • Android应用内存溢出OOM
    • 内存溢出的主要导致原因有如下几类:①应用代码存在内存泄露,长时间积累无法释放导致OOM;②应用的某些逻辑操作疯狂的消耗掉大量内存(譬如加载一张不经过处理的超大超高清图片等)导致超过阈值OOM
    • 解决思路①在内存引用上做些处理,常用的有软引用、弱引用 ②在内存中加载图片时直接在内存中做处理,如:边界压缩 ③动态回收内存,手动recyle bitmap,回收对象 ④优化Dalvik虚拟机的堆内存分配 ⑤自定义堆内存大小

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/877567.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【Python机器学习】循环神经网络(RNN)——超参数

几乎所有模型都可以根据数据和样本进行调整,它们都有各自的优势和相应的利弊权衡方式。寻找最优超参数集通常是一个棘手的问题,但是人类的直觉和经验可以为我们提供解决问题的方法。比如之前的例子: #设置任意输入序列的最大长度 maxlen100 …

WPS如何删除表格下的空白页

WPS Office(12.1.0.17827) ① 鼠标右键,选择段落 ② 行距:固定值;设置值:1磅;取消勾选,确定即可~

arcgisPro修改要素XY容差

1、在arcgisPro中XY容差的默认值为1个毫米,及0.001米。为了更精细的数据,需要提高这个精度,如何提高呢? 2、如果直接在数据库下新建要素类,容差只能调至0.0002米。所以,需要在数据库下新建要素数据集。 3…

使用 SuperCraft AI 设计书橱模型的指南

在现代家居设计中,书橱不仅是存放书籍的地方,更是展示个人品味和风格的重要家具。借助 SuperCraft AI,你可以轻松设计出独一无二的书橱。以下是详细的步骤指南,帮助你从零开始设计一个理想的书橱。 1. 创建项目 首先&#xff0c…

数据集 CULane 车道线检测 >> DataBall

数据集 CULane 车道线检测 自动驾驶 无人驾驶目标检测 CULane是用于行车道检测学术研究的大规模具有挑战性的数据集。它由安装在六辆由北京不同驾驶员驾驶的不同车辆上的摄像机收集。收集了超过55小时的视频,并提取了133,235帧。数据示例如上所示。我们将数据集分为…

数据结构——串的定义及存储结构

串的定义 串(string)——零个或多个任意字符组成的有限序列串是内容受限的线性表 串的几个术语 子串:串中任意几个连续字符组成的子序列称为该串的子串(真子串是指不包含自身的所有子串)主串:包含子串的串…

YoloV10改进策略:BackBone改进|注意力改进|HCANet全局与局部的注意力模块CAFM|二次创新|即插即用

摘要 在CAFM模型的基础上进行二次创新,我成功地开发了一个性能显著提升的改进版模型。这一创新不仅优化了特征提取和融合的方式,还极大地提高了模型的泛化能力和准确性。为了验证其有效性,我们将这一改进应用于流行的目标检测算法YoloV10,并取得了显著的精度提升。这一改进…

【专题】2024跨境出海供应链洞察-更先进供应链报告合集PDF分享(附原数据表)

原文链接:https://tecdat.cn/?p37665 当前,全球化商业浪潮促使跨境电商行业飞速发展,产业带与跨境电商接轨、平台半托管模式涌现、社交电商带来红利机会以及海外仓不断扩张,这使得产业带外贸工厂、内贸工厂、传统进出口企业和品…

Java项目基于docker 部署配置

linux新建文件夹 data cd datatouch Dockerfilesudo vim Dockerfile# 使用一个基础的 Java 镜像(根据自己项目中使用的是什么jdk版本设置,用于拉取执行jar包的jdk环境) FROM openjdk:8# 指定工作目录 VOLUME /data# 复制应用程序的 JAR 文件…

信息安全数学基础(14)欧拉函数

前言 在信息安全数学基础中,欧拉函数(Eulers Totient Function)是一个非常重要的概念,它与模运算、剩余类、简化剩余系以及密码学中的许多应用紧密相关。欧拉函数用符号 φ(n) 表示,其中 n 是一个正整数。 一、定义 欧…

机器学习特征构建与特征筛选

前言 上一篇文章讲述了原始特征分析和处理,保障后续拿到的是干净的特征变量,但实际这些特征对于建模不一定是有效的,所以需要在原始特征的基础上,结合业务场景做特征变量的衍生,提升数据的表达能力。此外,…

【C++】unordered系列

前言: 在C11及以后的标准中,unordered容器是标准模板库(STL)的一部分,提供了高效的数据结构选项,适用于需要快速查找和插入操作的场景。 unordered通常与关联容器一起使用,特别是unordered_map和…

图论篇--代码随想录算法训练营第六十一天打卡| Floyd 算法,A*算法

Floyd 算法(求多源汇最短路) 题目链接:97. 小明逛公园 题目描述: 小明喜欢去公园散步,公园内布置了许多的景点,相互之间通过小路连接,小明希望在观看景点的同时,能够节省体力&…

句子成分——每日一划(八)

目录 一、原句 二、第一部分 三、第二部分 一、原句 In class society everyone lives as a member of a particular class, and every kind of thinking, without exception, is stamped with the brand of a class. 来源:二、阶级和阶级斗争 二、第一部分 In…

谷粒商城のElasticsearch

文章目录 前言一、前置知识1、Elasticsearch 的结构2、倒排索引 (Inverted Index)2.1、 索引阶段2.2、查询阶段 二、环境准备1、安装Es2、安装Kibana3、安装 ik 分词器 三、项目整合1、引入依赖2、整合业务2.1、创建索引、文档、构建查询语句2.2、整合业务代码 后记 前言 本篇介…

初识php库管理工具composer的体验【爽】使用phpword模板功能替换里面的字符串文本

需求: 做了一个租赁的项目,里面要求签署个人授权协议,里面要填写姓名,手机号,身份证号,签署日期等参数,格式如下图 格式: 如上图,word中的字符串模板变量使用${varname…

Java设计模式—面向对象设计原则(三) -----> 依赖倒转原则DIP(完整详解,附有代码+案例)

文章目录 3.3 依赖倒转原则(DIP)3.3.1概述3.3.2 案例 3.3 依赖倒转原则(DIP) 依赖倒转原则:Dependency Inversion Principle,DIP 3.3.1概述 高层模块不应该依赖低层模块,两者都应该依赖其抽象;抽象不应该依赖细节,细…

演示:基于WPF的自绘的中国地铁轨道控件

一、目的:演示一个基于WPF的自绘的中国地铁轨道控件 二、效果演示 北京地铁 成都地铁 上海地铁 深圳地铁 南京地铁 长春地铁 哈尔滨地铁 武汉地铁 厦门地铁 香港地铁 三、功能 支持平移、缩放等操作 鼠标悬停显示线路信息和站点信息 按表格显示,按纸张…

MySQL —— 索引

索引的概念 MySQL的索引是⼀种数据结构,它可以帮助数据库高效地查询、更新数据表中的数据。索引通过 ⼀定的规则排列数据表中的记录,使得对表的查询可以通过对索引的搜索来加快速度。 MySQL索引类似于书籍的目录,通过指向数据行的位置&…

PCIe进阶之TL:First/Last DW Byte Enables Rules Traffic Class Field

1 First/Last DW Byte Enables Rules & Attributes Field 1.1 First/Last DW Byte Enables Rules Byte Enable 包含在 Memory、I/O 和 Configuration Request 中。本文定义了相应的规则。Byte Enable 位于 header 的 byte 7 。对于 TH 字段值为 1 的 Memory Read Request…