2022 大厂 Android 高级面试指南(六)

461 阅读14分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第17天,点击查看活动详情

第一篇面试指南在这: 2022 大厂 Android 高级面试指南(一)

第二篇面试指南在这: 2022 大厂 Android 高级面试指南(二)

第三篇面试指南在这: 2022 大厂 Android 高级面试指南(三)

第四篇面试指南在这: 2022 大厂 Android 高级面试指南(四)

第五篇面试指南在这: 2022 大厂 Android 高级面试指南(五)

重点强调一下:有需要面试PDF文档的掘友们:可以在评论区下方留言,或者后台私信我直接获取哈~

1.子线程发消息到主线程进行更新 UI,除了 handler 和 AsyncTask,还有什么?

用 Activity 对象的 runOnUiThread 方法更新

在子线程中通过 runOnUiThread()方法更新 UI:

如果在非上下文类中(Activity),可以通过传递上下文实现调用;复制代码

用 View.post(Runnable r)方法更新 UI

2.子线程中能不能 new handler?为什么?

不能,如果在子线程中直接 new Handler()会抛出异常 java.lang.RuntimeException: Can'tcreate handler inside thread that has not called

在没有调用 Looper.prepare()的时候不能创建 Handler,因为在创建 Handler 的源码中做了如下操作

Handler 的构造方法中

3.Android 中的动画有哪几类,它们的特点和区别是什么

Frame Animation(帧动画)主要用于播放一帧帧准备好的图片,类似GIF图片,优点是使用简单方便、缺点是需要事先准备好每一帧图片;

Tween Animation(补间动画)仅需定义开始与结束的关键帧,而变化的中间帧由系统补上,优点是不用准备每一帧,缺点是只改变了对象绘制,而没有改变View本身属性。因此如果改变了按钮的位置,还是需要点击原来按钮所在位置才有效。

Property Animation(属性动画)是3.0后推出的动画,优点是使用简单、降低实现的复杂度、直接更改对象的属性、几乎可适用于任何对象而仅非View类,主要包括ValueAnimator和ObjectAnimator

4.如何修改 Activity 进入和退出动画

可 以 通 过 两 种 方 式 , 一 是 通 过 定 义 Activity 的 主 题 , 二 是 通 过 覆 写 Activity 的overridePendingTransition 方法。

通过设置主题样式在 styles.xml 中编辑如下代码:

添加themes.xml文件:

在AndroidManifest.xml中给指定的Activity指定theme。 复制代码

覆写 overridePendingTransition 方法

overridePendingTransition(R.anim.fade,R.anim.hold);复制代码

5.Android与服务器交互的方式中的对称加密和非对称加密是什么?

对称加密,就是加密和解密数据都是使用同一个key,这方面的算法有DES。

非对称加密,加密和解密是使用不同的key。发送数据之前要先和服务端约定生成公钥和私钥,使用公钥加密的数据可以用私钥解密,反之。这方面的算法有RSA。ssh 和 ssl都是典型的非对称加密。

6.事件分发中的 onTouch 和 onTouchEvent 有什么区别,又该如何使用?

这两个方法都是在 View 的 dispatchTouchEvent 中调用的,onTouch 优先于 onTouchEvent执行。如果在 onTouch 方法中通过返回 true 将事件消费掉,onTouchEvent 将不会再执行。

另外需要注意的是,onTouch 能够得到执行需要两个前提条件,第一 mOnTouchListener 的值不能为空,第二当前点击的控件必须是 enable 的。因此如果你有一个控件是非 enable 的,那么给它注册 onTouch 事件将永远得不到执行。对于这一类控件,如果我们想要监听它的 touch 事件,就必须通过在该控件中重写 onTouchEvent 方法来实现。

7.属性动画,例如一个 button 从 A 移动到 B 点,B 点还是可以响应点击事件,这个原理是什么?

补间动画只是显示的位置变动,View 的实际位置未改变,表现为 View 移动到其他地方,点击事件仍在原处才能响应。而属性动画控件移动后事件相应就在控件移动后本身进行处理

都使用过哪些自定义控件

pull2RefreshListView

LazyViewPager

SlidingMenu

SmoothProgressBar

自定义组合控件

ToggleButton

自定义Toast复制代码

8.谈谈你在工作中是怎样解决一个 bug

异常附近多打印log信息;

分析log日志,实在不行的话进行断点调试;

调试不出结果,上 Stack Overflow 贴上异常信息,请教大牛

再多看看代码,或者从源代码中查找相关信息

实在不行就 GG 了,找师傅来解决!复制代码

9.嵌入式操作系统内存管理有哪几种, 各有何特性

页式,段式,段页,用到了MMU,虚拟空间等技术

10.开发中都使用过哪些框架、平台

EventBus(事件处理)

xUtils(网络、图片、ORM)

JPush(推送平台)

友盟(统计平台)

有米(优米)(广告平台)

百度地图

bmob(服务器平台、短信验证、邮箱验证、第三方支付)

阿里云 OSS(云存储)

ShareSDK(分享平台、第三方登录)

Gson(解析 json 数据框架)

imageLoader (图片处理框架)

zxing (二维码扫描)

anroid-asyn-http(网络通讯)

DiskLruCache(硬盘缓存框架)

Viatimo(多媒体播放框架)

universal-image-loader(图片缓存框架)

讯飞语音(语音识别)复制代码

11.谈谈你对 Bitmap 的理解, 什么时候应该手动调用 bitmap.recycle()

Bitmap 是 android 中经常使用的一个类,它代表了一个图片资源。 Bitmap 消耗内存很严重,如果不注意优化代码,经常会出现 OOM 问题,优化方式通常有这么几种:

使用缓存;

压缩图片;

及时回收;复制代码

至于什么时候需要手动调用 recycle,这就看具体场景了,原则是当我们不再使用 Bitmap 时,需要回收之。另外,我们需要注意,2.3 之前 Bitmap 对象与像素数据是分开存放的,Bitmap 对象存在java Heap 中而像素数据存放在 Native Memory 中, 这时很有必要调用 recycle 回收内存。 但是 2.3之后,Bitmap 对象和像素数据都是存在 Heap 中,GC 可以回收其内存。

12.请介绍下 AsyncTask 的内部实现和适用的场景

AsyncTask 内部也是 Handler 机制来完成的,只不过 Android 提供了执行框架来提供线程池来执行相应地任务,因为线程池的大小问题,所以 AsyncTask 只应该用来执行耗时时间较短的任务,比如 HTTP 请求,大规模的下载和数据库的更改不适用于 AsyncTask,因为会导致线程池堵塞,没有线程来执行其他的任务,导致的情形是会发生 AsyncTask 根本执行不了的问题

13.Activity间通过Intent传递数据大小有没有限制?

Intent在传递数据时是有大小限制的,这里官方并未详细说明,不过通过实验的方法可以测出数据应该被限制在1MB之内(1024KB),笔者采用的是传递Bitmap的方法,发现当图片大小超过1024(准确地说是1020左右)的时候,程序就会出现闪退、停止运行等异常(不同的手机反应不同),因此可以判断Intent的传输容量在1MB之内。

14.你一般在开发项目中都使用什么设计模式?如何来重构,优化你的代码?

较为常用的就是单例设计模式,工厂设计模式以及观察者设计模式,

一般需要保证对象在内存中的唯一性时就是用单例模式,例如对数据库操作的 SqliteOpenHelper 的对象。

工厂模式主要是为创建对象提供过渡接口,以便将创建对象的具体过程屏蔽隔离起来,达到提高灵活性的目的。

观察者模式定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新

15.Android 应用中验证码登陆都有哪些实现方案

从服务器端获取图片

通过短信服务,将验证码发送给客户端复制代码

16.定位项目中,如何选取定位方案,如何平衡耗电与实时位置的精度?

开始定位,Application 持有一个全局的公共位置对象,然后隔一定时间自动刷新位置,每次刷新成功都把新的位置信息赋值到全局的位置对象, 然后每个需要使用位置请求的地方都使用全局的位置信息进行请求。

该方案好处:请求的时候无需再反复定位,每次请求都使用全局的位置对象,节省时间。

该方案弊端:耗电,每隔一定时间自动刷新位置,对电量的消耗比较大。复制代码

按需定位,每次请求前都进行定位。这样做的好处是比较省电,而且节省资源,但是请求时间会变得相对较长。

17.andorid 应用第二次登录实现自动登录

前置条件是所有用户相关接口都走 https,非用户相关列表类数据走 http。

步骤

第一次登陆 getUserInfo 里带有一个长效 token,该长效 token 用来判断用户是否登陆和换取短 token

把长效 token 保存到 SharedPreferences

接口请求用长效 token 换取短token,短 token 服务端可以根据你的接口最后一次请求作为标示,超时时间为一天。

所有接口都用短效 token

如果返回短效 token 失效,执行第3步,再直接当前接口

如果长效 token 失效(用户换设备或超过一月),提示用户登录。复制代码

18.说说 LruCache 底层原理

LruCache 使用一个 LinkedHashMap 简单的实现内存的缓存,没有软引用,都是强引用。

如果添加的数据大于设置的最大值,就删除最先缓存的数据来调整内存。maxSize 是通过构造方法初始化的值,他表示这个缓存能缓存的最大值是多少。

size 在添加和移除缓存都被更新值, 他通过 safeSizeOf 这个方法更新值。 safeSizeOf 默认返回 1,但一般我们会根据 maxSize 重写这个方法,比如认为 maxSize 代表是 KB 的话,那么就以 KB 为单位返回该项所占的内存大小。

除异常外,首先会判断 size 是否超过 maxSize,如果超过了就取出最先插入的缓存,如果不为空就删掉,并把 size 减去该项所占的大小。这个操作将一直循环下去,直到 size 比 maxSize 小或者缓存为空。

19.jni 的调用过程?

安装和下载 Cygwin,下载 Android NDK。

ndk 项目中 JNI 接口的设计。

使用 C/C++实现本地方法。

JNI 生成动态链接库.so 文件。

将动态链接库复制到 java 工程,在 java 工程中调用,运行 java 工程即可。复制代码

20.一条最长的短信息约占多少byte?

中文70(包括标点),英文160,160个字节。

21.即时通讯是是怎么做的?

使用asmark 开源框架实现的即时通讯功能.该框架基于开源的 XMPP 即时通信协议,采用 C/S 体系结构,通过 GPRS 无线网络用 TCP 协议连接到服务器,以架设开源的Openfn'e 服务器作为即时通讯平台。

客户端基于 Android 平台进行开发。负责初始化通信过程,进行即时通信时,由客户端负责向服务器发起创建连接请求。系统通过 GPRS 无线网络与 Internet 网络建立连接,通过服务器实现与Android 客户端的即时通信脚。

服务器端则采用 Openfire 作为服务器。 允许多个客户端同时登录并且并发的连接到一个服务器上。服务器对每个客户端的连接进行认证,对认证通过的客户端创建会话,客户端与服务器端之间的通信就在该会话的上下文中进行。

22.怎样对 android 进行优化?

对 listview 的优化。

对图片的优化。

对内存的优化。

具体一些措施

尽量不要使用过多的静态类static

数据库使用完成后要记得关闭 cursor

广播使用完之后要注销复制代码

23.如果有个100M大的文件,需要上传至服务器中,而服务器form表单最大只能上传2M,可以用什么方法。

首先来说使用http协议上传数据,特别在android下,跟form没什么关系。

传统的在web中,在form中写文件上传,其实浏览器所做的就是将我们的数据进行解析组拼成字符串,以流的方式发送到服务器,且上传文件用的都是POST方式,POST方式对大小没什么限制。

回到题目,可以说假设每次真的只能上传2M,那么可能我们只能把文件截断,然后分别上传了,断点上传。

24.MVP模式架构

MVP架构由MVC发展而来。在MVP中,M代表Model,V代表View,P代表Presenter。

模型层(Model):主要是获取数据功能,业务逻辑和实体模型。

视图层(View):对应于Activity或Fragment,负责视图的部分展示和业务逻辑用户交互

控制层(Presenter):负责完成View层与Model层间的交互,通过P层来获取M层中数据后返回给V层,使得V层与M层间没有耦合。

在MVP中 ,Presenter层完全将View层和Model层进行了分离,把主要程序逻辑放在Presenter层实现,Presenter与具体的View层(Activity)是没有直接的关联,是通过定义接口来进行交互的,从而使得当View层(Activity)发生改变时,Persenter依然可以保持不变。View层接口类只应该只有set/get方法,及一些界面显示内容和用户输入,除此之外不应该有多余的内容。绝不允许View层直接访问Model层,这是与MVC最大区别之处,也是MVP核心优点。

25.虚拟机

Dalvik

Android4.4及以前使用的都是Dalvik虚拟机,我们知道Apk在打包的过程中会先将java等源码通过javac编译成.class文件,但是我们的Dalvik虚拟机只会执行.dex文件,这个时候dx会将.class文件转换成Dalvik虚拟机执行的.dex文件。Dalvik虚拟机在启动的时候会先将.dex文件转换成快速运行的机器码,又因为65535这个问题,导致我们在应用冷启动的时候有一个合包的过程,最后导致的一个结果就是我们的app启动慢,这就是Dalvik虚拟机的JIT特性(Just In Time)。

ART

ART虚拟机是在Android5.0才开始使用的Android虚拟机,ART虚拟机必须要兼容Dalvik虚拟机的特性,但是ART有一个很好的特性AOT(ahead of time),这个特性就是我们在安装APK的时候就将dex直接处理成可直接供ART虚拟机使用的机器码,ART虚拟机将.dex文件转换成可直接运行的.oat文件,ART虚拟机天生支持多dex,所以也不会有一个合包的过程,所以ART虚拟机会很大的提升APP冷启动速度。

ART优点:

加快APP冷启动速度

提升GC速度

提供功能全面的Debug特性

ART缺点:

APP安装速度慢,因为在APK安装的时候要生成可运行.oat文件

APK占用空间大,因为在APK安装的时候要生成可运行.oat文件

arm处理器