介绍自己负责的部分,如何实现的。
框架的搭建
排查问题以及结解决方式
兼容性保证
性能优化
上线之后模块导致crash的比例
自定义view viewGroup
这个就是约定的几个方法,onMeasure,onLayout,onDraw,measure,layout,draw
同时注意写方法的调用时机以及区别,比如onMeasure是个模版方法是在measure下调用的,这个方法在viewGroup里面,
自定义的这些就已经足够了,如果还扩展一些更新问题,子线程能不能更新,是可以的,在ViewRootImpl没创建之前可以更新,不同sdk这个类可能名字不一样。
1.自定义属性
2.onLayout(Viewgroup)
3.onMesure
4.onDraw
5.交互:onIntercepterTouchEvent()onTouchEvent()
activity的启动流程
这个肯定不是说activity的生命周期,是启动加载过程,大致说下流程,具体的要自己看代码了,大致过程有:
这里可能分好几种情况,其实都差不很多,这里就说一种情况,startActivity这个怎么启动Activity的,
startActivity->ActivityManagerService->ActivityThread->Activity,大概参与就这几个核心类,里面经过了两层binder通信,最后路由到IApplicationThread,然后到ActivityThread中的H消息队列中启动Activity,细节很多,可以在评论询问。
从桌面点击到activity启动的过程
- 1.Launcher线程捕获onclick的点击事件,调用Launcher.startActivitySafely,进一步调用Launcher.startActivity,最后调用父类Activity的startActivity。
- 2.Activity和ActivityManagerService交互,引入Instrumentation,将启动请求交给Instrumentation,调用Instrumentation.execStartActivity。
- 3.调用ActivityManagerService的startActivity方法,这里做了进程切换(具体过程请查看源码)。
- 4.开启Activity,
事件传递及滑动冲突的处理
事件传递理解成责任链式调用就好,也就是从最内层到外层时间委派,如果事件consume了,那么就给这个view处理,不然从外向内冒泡,
冲突处理举个实例就好,比如SlideMenu与banner或者ListView与Scrollview的冲突等等,说出基本思路就行,这些解决一般都是重写那几个事件方法,然后各种判断就好
插件化(activity如何加载及资源处理)
Activity使用占坑hook加载,也可以使用静态代理,静态代理就需要自定义classloader,记住这个加载模式就行,再多细节在评论回复吧
,资源处理就是assetmanager的创建,然后资源冲突处理,简单的可以构建多个assetmanager就没有冲突问题,应为隔离了,如果使用一个那么
打包aapt定制一下就行,还有很多细节,在评论回复吧,说不完了。
调用onCreate方法热补丁原因:
因为一个dvm中存储方法id用的是short类型,导致dex中方法不能超过65536个原理:
将编译好的class文件拆分打包成两个dex,绕过dex方法数量的限制以及安装时的检查,在运行时再动态加载第二个dex文件中。使用Dexclassloader。
动态加载(也叫插件化技术)动态加载主要解决3个技术问题:
- 1,使用ClassLoader加载类。
- 2,资源访问。
- 3,生命周期管理。
参考
1、Android动态加载学习总结(一):类加载器
2、ZeusPlugin:掌阅Android App插件补丁实践
3、Android 插件化原理解析——Hook机制之AMS&PMS
4、Android Hotfix 新方案——Amigo 源码解读
5、Android Hotfix 新方案——Amigo 源码解读
6、插件化由理论到实践【更新于2016年9月3日】
内存优化 ,如何避免oom
内存优化太多要说的了,有套路的回答,基本就是避免跟gc配合好工作.
比如:尽量复用对象,处理无用对象,避免内存泄漏,压缩对象等等.
尽量将大对象特殊处理,比如bitmap占用内存较多,可以jni层与java层配合一起,大小压缩,质量压缩,imsimplesize的大小定义,规范等等,程序中有内存管理模块,避免内存压力大的时候
,能够释放内存,避免oom发生的几率,还有很多方面,在评论回复吧。
内存泄漏如何处理及如何排查
内存泄漏最大的问题就是无用对象常驻内存,导致内存压力很大,最后可能导致oom发生。
尽量将对象生命周期可以在控制的能力之内,也很多场景,比如:context 除了特殊情况用activity,其他我们没理由不用application。
排查导出堆空间,然后mat分析,程序里面用leackcanary定位。
handler问题
这个需要回复两个基本的,首先handler的创建需要loop,loop怎么创建的,同时这个里面怎么保证loop线程安全的,还有就是消息如何分发的,也就是消息发送到接受的流程,
还有callback对消息处理的影响,这些足够了,还可以说可以跨进程,这样就更棒了,具体的在回复说,太多了。
图片加载用的什么以及原理
图片加载的太多了,说个自己非常熟悉的就行,不要给自己挖坑,都懂的,比如你熟悉uil,那就说具体的加载过程,
套路都差不多,都是创建图片task,先从缓存取出来,取不到就去网络下载,下载完之后,同时缓存起来,这里需要说下,线程池,队列,pause,resume的具体细节,比如跟view,activity的绑定关系。回复具体说,也很多.
从一堆数据里怎么查找最大的n个数
这个用归并排序,或者直接快排,没啥还说的。不会的自己google看算法,算法后面我会写出来到文章里面。
快速排序
基本思想挖坑,分而治之,按照这个思路看代码就行
字符串匹配
这个kmp算法,或者最基本的吧,不考虑时间,空间复杂度的条件下,但是不要说这个,太low了点。其实这些算法背下来就好,不是业务场景的,意义不大,但是必须要会,不然吃亏了
热点
如何保证Service不被杀死 Android 进程不死?
从3个层面入手:
A.提供进程优先级,降低进程被杀死的概率
- 方法一:监控手机锁屏解锁事件,在屏幕锁屏时启动1个像素的 Activity,在用户解锁时将 Activity 销毁掉。
- 方法二:启动前台service。
- 方法三:提升service优先级:在AndroidManifest.xml文件中对于intent-filter可以通过
B. 在进程被杀死后,进行拉活。
- 方法一:注册高频率广播接收器,唤起进程。
如网络变化,解锁屏幕,开机等 - 方法二:双进程相互唤起。
- 方法三:依靠系统唤起。
- 方法四:onDestroy方法里重启service:service +broadcast 方式,就是当service走ondestory的时候,发送一个自定义的广播,当收到广播的时候,重新启动service;
C. 依靠第三方根据终端不同。
在小米手机(包括 MIUI)接入小米推送、华为手机接入华为推送;
其他手机可以考虑接入腾讯信鸽或极光推送与小米推送做 A/B Test。
参考博客:Android 进程保活招式大全
Activity、Application以及BroadcastReceiver生命周期
http://www.jianshu.com/p/fcac1a8437ba
ButterKnife原理
ButterKnife对性能的影响很小,因为没有使用使用反射,而是使用的Annotation Processing Tool(APT),注解处理器,javac中用于编译时扫描和解析Java注解的工具。
在编译阶段执行的,它的原理就是读入Java源代码,解析注解,然后生成新的Java代码。
新生成的Java代码最后被编译成Java字节码,注解解析器不能改变读入的Java 类,比如不能加入或删除Java方法。
Android6.0新特性
大量漂亮流畅的动画支持快速充电的切换支持文件夹拖拽应用相机新增专业模式
Android7.0新特性
分屏多任务增强的Java8语言模式夜间模式
android中有哪几种解析xml的类,官方推荐哪种?以及它们的原理和区别
DOM解析
优点:
1.XML树在内存中完整存储,因此可以直接修改其数据和结构.
2.可以通过该解析器随时访问XML树中的任何一个节点.
3.DOM解析器的API在使用上也相对比较简单.
缺点:
如果XML文档体积比较大时,将文档读入内存是非常消耗系统资源的.
使用场景:
DOM 是用与平台和语言无关的方式表示 XML 文档的官方 W3C 标准.
DOM 是以层次结构组织的节点的集合.
这个层次结构允许开发人员在树中寻找特定信息.分析该结构通常需要加载整个文档和构造层次结构,然后才能进行任何工作.DOM是基于对象层次结构的.
SAX解析
优点:
SAX 对内存的要求比较低,因为它让开发人员自己来决定所要处理的标签.
特别是当开发人员只需要处理文档中所包含的部分数据时,SAX 这种扩展能力得到了更好的体现.
缺点:
用SAX方式进行XML解析时,需要顺序执行,所以很难访问到同一文档中的不同数据.
此外,在基于该方式的解析编码过程也相对复杂.
使用场景:
对于含有数据量十分巨大,而又不用对文档的所有数据进行遍历或者分析的时候,使用该方法十分有效.该方法不用将整个文档读入内存,而只需读取到程序所需的文档标签处即可.
Xmlpull解析
android SDK提供了xmlpull api,xmlpull和sax类似,是基于流(stream)操作文件,然后根据节点事件回调开发者编写的处理程序.
因为是基于流的处理,因此xmlpull和sax都比较节约内存资源,不会象dom那样要把所有节点以对橡树的形式展现在内存中.xmlpull比sax更简明,而且不需要扫描完整个流.
引起内存泄漏的情况
- 对于使用了BraodcastReceiver,ContentObserver,File,游标 Cursor,Stream,Bitmap等资源的使用,应该在Activity销毁时及时关闭或者注销。
- 静态内部类持有外部成员变量(或context):可以使用弱引用或使用ApplicationContext。
- 内部类持有外部类引用,异步任务中,持有外部成员变量。
- 集合中没用的对象没有及时remove。不用的对象及时释放,如使用完Bitmap后掉用recycle(),再赋null。
- handler引起的内存泄漏,MessageQueue里的消息如果在activity销毁时没有处理完,就会引起内存的泄漏,可以使用弱引用解决。
- 设置过的监听不用时,及时移除。如在Destroy时及时remove。尤其以addListener开头的,在Destroy中都需要remove。
activity泄漏可以使用LeakCanary。
Android 内存溢出解决方案(OOM) 整理总结
在内存引用上做些处理,常用的有软引用、弱引用 在内存中加载图片时直接在内存中作处理,如:边界压缩 动态回收内存 优化Dalvik虚拟机的堆内存分配 自定义堆内存大小。
如果图片很大,比如他们的占用内存算下来就直接OOM了,那么我们肯定不能直接加载它。解决主法还是有很多的,系统也给我们提供了一个类BitmapRegionDecoder,可以用来分块加载图片。
Activity/Window/View三者的差别?
Activity像一个工匠(控制单元),Window像窗户(承载模型),View像窗花(显示视图) LayoutInflater像剪刀,Xml配置像窗花图纸。
JVM 和Dalvik虚拟机的区别
- JVM:.java -> javac -> .class -> jar -> .jar架构: 堆和栈的架构.
- DVM:.java -> javac -> .class -> dx.bat -> .dex架构: 寄存器(cpu上的一块高速缓存)
怎么考虑数据传输的安全性?
如果应用对传输的数据没有任何安全措施,攻击者设置的钓鱼网络中更改DNS服务器。这台服务器可以获取用户信息,或充当中间人与原服务器交换数据。在SSL/TLS通信中,客户端通过数字证书判断服务器是否可信,并采用证书的公钥与服务器进行加密通信。
ART和Dalvik区别?
- art上应用启动快,运行快,但是耗费更多存储空间,安装时间长,总的来说ART的功效就是”空间换时间”。
ART: Ahead of TimeDalvik: Just in Time什么是Dalvik:Dalvik是Google公司自己设计用于Android平台的Java虚拟机。
- Dalvik虚拟机是Google等厂商合作开发的Android移动设备平台的核心组成部分之一,它可以支持已转换为.dex(即Dalvik Executable)格式的Java应用程序的运行,.dex格式是专为Dalvik应用设计的一种压缩格式,适合内存和处理器速度有限的系统。
Dalvik经过优化,允许在有限的内存中同时运行多个虚拟机的实例,并且每一个Dalvik应用作为独立的Linux进程执行。独立的进程可以防止在虚拟机崩溃的时候所有程序都被关闭。
什么是ART?
Android操作系统已经成熟,Google的Android团队开始将注意力转向一些底层组件,其中之一是负责应用程序运行的Dalvik运行时。Google开发者已经花了两年时间开发更快执行效率更高更省电的替代ART运行时。ART代表Android Runtime,其处理应用程序执行的方式完全不同于Dalvik.
Dalvik是依靠一个Just-In-Time(JIT)编译器去解释字节码。开发者编译后的应用代码需要通过一个解释器在用户的设备上运行,这一机制并不高效,但让应用能更容易在不同硬件和架构上运行。ART则完全改变了这套做法,在应用安装的时候就预编译字节码到机器语言,这一机制叫Ahead-Of-Time(AOT)编译。在移除解释代码这一过程后,应用程序执行将更有效率,启动更快。
ART优点:
系统性能的显著提升应用启动更快、运行更快、体验更流畅、触感反馈更及时。更长的电池续航能力支持更低的硬件
ART缺点:
更大的存储空间占用,可能会增加10%-20%更长的应用安装时间.
JavaScript调用Java方法?
需要使用WebView.addJavascriptInterface方法设置JavaScript调用的Java方法,代码如下:
webView.addJavascriptInterface(new Object(){
//JavaScript调用的方法
public String process(String value) {
//处理代码
return result;
}
}, "demo");
//demo是Java对象映射到JavaScript中的对象名
可以使用下面的JavaScript代码调用process方法,代码如下: