Android知识点汇总

本文全面覆盖Android开发核心知识,从Java基础、数据结构算法到Android关键模块,深入探讨网络、数据库优化,架构设计与模式,性能提升策略。详解模块化、热修复技术,JNI原理,及系统开发要点。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

目录

一、Java相关

二、Android重要知识模块

1.Android基础

2.网络

3.数据库

SharedPreferences

三、架构设计和设计模式

1.常用框架

2.Jetpack

3.注解与事件总线框架

注解与依赖注入

 事件

3.1RxJava

3.2 协程

特点

用法

3.3 RxJava 和协程优缺点

4.设计模式

四、性能优化

五、模块化、组件化、插件化、热修复区别

六、JNI

1.JNI注册方式

2.C调用JAVA

3.System.loadLibrary原理

七、开发相关问题

1. 系统开发相关

2.开发遇到的问题

八、调试技巧


一、Java相关

Java基础知识总结

 数据结构与算法总结

二、Android重要知识模块

1.Android基础

Android基础知识总结

Android Framework知识总结

Android重要系统应用模块

Android 架构

Android 各版本特性

2.网络

Android网络开发学习总结

3.数据库

  1. sqlite升级:涉及表和字段。表和字段的新增与删除能直接修改,字段不支持直接修改,需要通过中间文件做转换。
  2. 数据库框架对比和源码分析:如LiteOrm、GreenDao、Realm等。
  3. 数据库的优化:a.使用索引;b.语句的拼接使用StringBuilder代替String;c.查询时返回更少的结果集及更少的字段;d.少用cursor.getColumnIndex;e.异步线程;
  4. 数据库数据迁移问题:创建临时表做中转。
  5. 如何导入外部数据库:1. 把原数据库包括在项目源码的 res/raw 目录下,2.在进入应用时,若data/data下没有数据库,则用写文件的方式把数据库拷入,若已有则直接打开。

SharedPreferences

sharepreferences 是线程安全的,底层(SharedPreferencesImpl)用synchronized来保证同步。但不是进程安全的,可通过ContentProvider 实现多进程共同访问。

  1. 不支持跨进程,MODE_MULTI_PROCESS 也没用。跨进程频繁读写可能导致数据损坏或丢失。
  2. 初始化的时候会读取 sp 文件,可能导致后续 getXXX() 方法阻塞。建议提前异步初始化 SharedPreferences。
  3. sp 文件的数据会全部保存在内存中,所以不宜存放大数据。
  4. edit() 方法每次都会新建一个 EditorImpl 对象。建议一次 edit(),多次 putXXX() 。
  5. 无论是 commit() 还是 apply() ,针对任何修改都是全量写入。建议针对高频修改的配置项存在子啊单独的 sp 文件。
  6. commit() 同步保存,有返回值。apply() 异步保存,无返回值。
  7. onPause() 、onReceive() 等时机会等待异步写操作执行完成,可能造成卡顿或者 ANR。

Android中的SharedPreferences是否支持多进程、多线程

三、架构设计和设计模式

1.常用框架

Android 常用开源框架

2.Jetpack

一系列开发组件的统称,方便快速开发应用。

Jetpack学习总结

3.注解与事件总线框架

注解与依赖注入

注解与依赖注入

几种注解框架对比,Annotations 和 ButterKnife 为编译时注解,比XUtils(运行时注解)效率高。

 事件

  1. RxJava的功能与原理实现: 使用可观察序列组成的一个异步地,基于事件的响应式编程框架,逻辑简单,流式结构。
  2. RxJava的作用,与平时使用的异步操作来比的优缺点。
  3. 说说EventBus作用,实现方式,代替EventBus的方式:观察者模式,依赖反射,订阅后处理。
  4. 如果一个订阅者需要注册多个事件的时候,Rxjava需要一个个单独的注册,而EventBus则可以实现一个订阅者订阅多个事件,和一个事件对应多个订阅者。所以在Rxjava的基础上有了Rxbus来作为事件总线的库。RxBus在订阅者数量很大的情况下性能下降很明显,比不过EventBus。
  5. RxAndroid 可理解为专供Android平台的RxJava,针对平台增加了少量类。

3.1RxJava

使用可观察序列组成的一个异步地、基于事件的响应式编程框架。

// RxJava的链式操作
        Observable.create(new ObservableOnSubscribe<Integer>() {
        // 1\. 创建被观察者 & 生产事件
            @Override
            public void subscribe(ObservableEmitter<Integer> emitter) throws Exception {
                emitter.onNext(1);
                emitter.onNext(2);
                emitter.onNext(3);
                emitter.onComplete();
            }
        }).subscribe(new Observer<Integer>() {
            // 2\. 通过通过订阅(subscribe)连接观察者和被观察者
            // 3\. 创建观察者 & 定义响应事件的行为
            @Override
            public void onSubscribe(Disposable d) {
                Log.d(TAG, "开始采用subscribe连接");
            }
            // 默认最先调用复写的 onSubscribe()
 
            @Override
            public void onNext(Integer value) {
                Log.d(TAG, "对Next事件"+ value +"作出响应"  );
            }
 
            @Override
            public void onError(Throwable e) {
                Log.d(TAG, "对Error事件作出响应");
            }
 
            @Override
            public void onComplete() {
                Log.d(TAG, "对Complete事件作出响应");
            }
 
        });
    }
}
 
注:整体方法调用顺序:观察者.onSubscribe()> 被观察者.subscribe()> 观察者.onNext()>观察者.onComplete() 
 

3.2 协程

Android 协程详解,

kotlin协程是一种并发设计模式,可以用来在Android上简化异步执行的代码。有助于管理长时间运行的任务。可实现类似RxJava效果。

特点
  1. 轻量:可以在单线程上运行多个协程。
  2. 内存泄露少;
  3. 内置取消操作;
  4. 支持jetpack;

缺点:

  1. 本质是单线程的,无法利用多核资源;
  2. 无法避免阻塞:虽然协程可以异步处理I/O操作,但对于一些需要长时间运行的任务(如计算、网络请求等),仍然可能导致整个程序阻塞。
  3. 难以调试:由于协程的执行流程比较复杂,调试起来相对困难。

用法

kotlin协程

3.3 RxJava 和协程优缺点

协程

  1. 简洁的语法:Kotlin协程的语法简洁明了,易于学习和使用。
  2. 高性能:由于协程在单线程上运行,避免了线程创建和管理的开销,提高了执行效率。
  3. 方便的取消和恢复:协程支持取消和恢复,这使得在网络请求中处理异常情况变得简单。
    在使用Kotlin协程进行网络请求时,可以考虑使用如Coroutines + Retrofit或Coroutines + OkHttp等组合,它们提供了方便的API来处理异步请求。

RxJava
RxJava是ReactiveX在Java平台上的实现,它提供了一种基于观察者模式的异步编程模型。通过使用可观察序列(Observables)和操作符(Operators),RxJava能够以声明式方式处理异步数据流。
RxJava的主要优点包括:

  1. 声明式编程:RxJava使用声明式语法,使得异步操作和数据流的处理更加直观。
  2. 丰富的操作符:RxJava提供了大量操作符,可以组合和变换数据流以满足复杂的需求。
  3. 社区支持:由于RxJava在Java社区中的广泛应用,有大量的资源和文档可供参考。
  4. 在使用RxJava进行网络请求时,通常会与Retrofit或OkHttp等库结合使用。通过将网络请求封装为Observable或Flowable,可以轻松地处理异步数据流。

协程适用于处理高并发的IO密集型应用场景,尤其在需要大量并发连接的情况下具有优势。不宜用于对于计算密集型的应用场景或者需要利用多核资源的情况。

4.设计模式

设计模式学习总结

四、性能优化

Android性能优化学习总结

  1. 如何对Android 应用进行性能分析以及优化?
    1. 分类:
      1. 性能问题:布局与绘制;启动速度; apk启动耗时:am start -W 中的waittime
      2. 内存问题:内存泄漏,内存浪费。 查看内存使用情况
      3. 耗电问题:
      4. 网络优化:
      5. 存储优化:
      6. apk大小;
      7. 稳定性优化;
    2. 检测工具:Lint代码检查,GPU过度绘制选项查看过渡绘制,
  2. ddms 和 traceView
  3. 性能优化如何分析systrace?
  4. Java多线程引发的性能问题,怎么解决?
    1. 利用线程池解决频繁创建与销毁问题;
    2. 减少无意义的同步,与伪共享;
  5. 启动页白屏及黑屏解决? 设置窗口背景颜色为透明,在布局未加载出来时,显示当前应用背景。
  6. App启动与发布后崩溃异常捕捉:在Application 启动时初始化Thread.UncaughtExceptionHandler 类,用其去捕捉异常,不能捕获native层。native层使用sigaction捕捉异常信号,或使用Bugly、google-breakpad等第三方工具。 参考crash log收集总结 
  7. 现在下载速度很慢,试从网络协议的角度分析原因,并优化。 网络拥塞控制;ARP;DNS解析;缓存……

五、模块化、组件化、插件化、热修复区别

模块化、组件化、插件化、热修复区别

  1. 热修复:目的是为了解决线上的bug或者小功能的更新,做到不用为了解决小bug或者小功能而频繁发布版本。核心技术分三类:代码修复、资源修复和动态链接库修复。每个核心技术有不同的方案,每种方案又有不同的实现。
    1. 代码修复:主要有三个方案:底层替换(直接在Native层修改原有类,不需要重新加载类。阿里系为主。)、类加载(基于Dex分包方案,主要有是Google官方方案、Dex自动拆包和动态加载方案。不能即时生效。)、Instant Run。
    2. 资源修复:替换系统AssetManger,加入patch的资源
    3. 动态链接库修复:先加载patch所在的so;
  2. 插件化原理分析:主要涉及类加载和资源加载。插件化目的是为了解耦业务模块,将一个应用里面不同的业务模块都做成一个apk。可并行开发,动态加载。
  3. 模块化实现:分模块开发,解耦。
  4. 项目组件化的理解:一种开发模式,把每个模块使用到的共同的功能抽取出来做成一个Lib去共同依赖,每个业务模块互不依赖、互相解耦,在开发的时候可以安排不同的开发人员去开发不同的模块,开发完毕以后单模块测试,最后整合到一起总体测试上线。
  5. 对于应用更新这块是如何做的?(解答:灰度,强制更新,分区域更新)?

六、JNI

1.JNI注册方式

  1. jni中注册native函数方法: 注册JNI函数的两种方式
    1. 静态注册:每个class都得用javah生成一个头文件,名字长,首次调用慢。类似 android_com_media_Target_test() ,通过函数命令规则查找响应函数。
    2. 动态注册:要在jni_onload 中注册。有类似 { "hello", "()Ljava/lang/String;", (void*)native_hello} 对应关系。 {"native_start",  "()V", (void *)android_media_AudioTrack_start},

2.C调用JAVA

  1. jni如何调用java层代码? C/C++调用JAVA
    1. 获取字节码对象;
    2. 通过字节码对象找到方法对象;
    3. 通过字节码文件创建object对象;
    4. 通过对象调用方法。

3.System.loadLibrary原理

Runtime.loadLibrary0 先用findLibrary去查找so是否存在,然后调用nativeLoad去加载库。

nativeLoad 方法参考:System.loadLibrary 加载 .so 原理

七、开发相关问题

1. 系统开发相关

  1. Android5种签名类型 :platform、media, shared, testkey/releasekey
  2. App 是如何沙箱化,为什么要这么做?  设置UID,底层是基于Linux内核的权限机制。
  3. 权限管理系统(底层的权限是如何进行 grant 的)? 参考 Android权限之底层实现概览
  4. 内存对象的循环引用及避免:内存回收机制的可达性算法。使用弱指针,程序中手动释放。
  5. 系统启动流程是什么?(init--Zygote进程 –> SystemServer进程 –> 各种系统服务 –> 应用进程)
  6. 一个应用程序安装到手机上时发生了什么
  7. Android为每个应用程序分配的内存大小是多少?
    dalvik.vm.heapstartsize=8m    ----起始分配内存
    dalvik.vm.heapgrowthlimit=192m ---- 一般情况app申请的最大内存 dalvik.vm.heapsize=512m 
  8. Android中进程内存的分配,能不能自己分配定额内存?
  9. 进程保活的方式:Android进程分类?前台,可视,服务,后台,空进程
  10. 如何保证一个后台服务不被杀死?(相同问题:如何保证service在后台不被kill?)比较省电的方式是什么?
  11. 什么是协程?:可看做是轻量级的线程,一个线程内能包含多个协程。协程是串行执行的,由用户自己控制调度。
  12. App中唤醒其他进程的实现方式:通过intent的不同用法,参考 App相互唤醒的几种方式

2.开发遇到的问题

  1. 工作历史问题技术记录
  2. 低版本SDK如何实现高版本api:用@SuppressLint 和 @TargetApi 后加入版本判断。
  3. 为什么不能在子线程更新UI?  在更新UI时都会调用 ViewRootImpl 中的 checkThread()方法来判断当前线程是否是主线程,若不是就会抛异常。在onCreate方法中可以在子线程中更新UI,因为此时ViewRootImpl还没有创建,无法做判断。ViewRootImpl是在handleResumeActivity方法中的makeVisible里面创建的。
  4. 有什么解决方法可以避免OOM?
  5. Oom 是否可以try catch?为什么? 可以,但不应该这样做。
  6. 怎么去除重复代码? 抽象基类,布局文件,style等。

八、调试技巧

  1. pm, dumpsys 等相关命令
  2. 编译命令
  3. trace, systrace 等
  4. bugreport
  5. debuggerd
  6. gdb
  7. addline
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值