学Android
文章平均质量分 73
为啥强制昵称
这个作者很懒,什么都没留下…
展开
-
Object.wait和Thread.sleep源码
面试被问到了wait和sleep区别,才知道这种使用场景完全不同的东西还能问区别…不过,确实没看过这俩的源码,来看一下。解释器映射op的过程我这里看的是art源码,而非jvm源码。本人对bytecode到真正执行代码的映射暂无认知,经高人指点是所有的解释器实现是在interpreter目录中。入口是interpreter.cpp#EnterInterpreterFromInvoke -> Execute -> ExecuteSwitch -> interpreter_switch_i原创 2021-12-08 17:49:03 · 285 阅读 · 0 评论 -
跨语言通信——GC
GC与native指针在gc的时候释放native指针。有几个方案,基本是finalize和PhantomReference。Bitmap在8.0以后,Bitmap的真实数据是存在native的,所以要有一个绑定到java对象,监听gc并释放native内存的操作。这里采用的是sun.misc中提供的一个PhantomReference的方式。代码路径如下:Bitmap.java#createBitmapBitmap.cpp#Bitmap_creatorBitmap.cpp#createBi原创 2021-08-16 11:49:04 · 173 阅读 · 0 评论 -
kt的协程是咋回事
kt的协程是咋回事背景跟协程啥关系几十行的轮子背景偶然遇到一个需求,把串行的大任务拆分成更小颗粒度的小任务依次串行执行。听起来没啥用,但是在现实场景中,是个很有效改善TTR的工作。因为主线程中的任务是不能被打断的,而所有用户操作都需要插入到队列中处理,一旦一个计算任务又大又长还在主线程,用户一定很难受。由此react提出了fiber,官宣也挺有用的。跟协程啥关系其实最舒服的接口就是协程类的接口,通过套嵌或顺序发起任务进行大任务拆分,以语义化dsl的方式减少阅读和理解成本,以闭包在任务间传递参数。而且原创 2021-06-11 11:10:19 · 313 阅读 · 1 评论 -
[源码]DownloadManager
各家APP都有自己的下载工具,都不用系统的,然而貌似系统的下载各方面都要好一些,看一下,为自己写下载组件做准备。方法下载肯定会有IPC,也肯定会有日志系统。DownloadManager使用的是ContentProvider的形式。业务调用的都是DownloadManager对于ContentProvider的封装ContentProvider事实上是个非常厉害的存在,可以做任何简原创 2016-05-11 10:34:18 · 3251 阅读 · 0 评论 -
[源码]OKHttp及Http协议笔记
合理设计使用Builder把成员变量的setter从复杂的逻辑对象里剥离出来,让结构清晰一些,也做到了对象的immutable——OkHttpClient.Builder 但是,可能有个FieldWrapper更加方便:Buildee中需要Builder配置的所有Field都放到FieldWrapper中。Builder在构造函数中new一个FieldWrapper,在build时,把Field原创 2016-06-21 19:37:36 · 2641 阅读 · 0 评论 -
[源码]SQLiteDatabase
不是sqlite源码!!!本人sql太渣,通过SQLiteDatabase 学习一下硬知识SQLiteSessionWAL:https://zh.wikipedia.org/wiki/%E9%A2%84%E5%86%99%E5%BC%8F%E6%97%A5%E5%BF%97在开启WAL之后,sqlite支持并行的读和写事务;否则,只有只读事务可以并行。具体解释套嵌事务的成功必须是每个子事务都是原创 2016-08-24 15:51:16 · 440 阅读 · 0 评论 -
[源码]LeakCanary
LeakCanary 源码原创 2016-12-19 13:56:03 · 311 阅读 · 0 评论 -
[源码]ARouter
ARouter是大阿里开源的Android App“架构”类框架。最主要的就是解除依赖的,包括了页面的依赖、功能的依赖;还有hook、降级、绑定用的语法糖等。结构合理设计不想使用运行时反射,就在编译时,用Annotation把信息都生成到一个Config文件中。这其实类似于js的eval,是个很好的办法——RouterProcessor技巧原创 2017-03-16 17:44:46 · 518 阅读 · 0 评论 -
[源码]Concurrent包之BlockingQueue、BlockingDeque
Java程序员不懂concurrent包可能很难说的过去,准备搞一系列文章,按照某外国小哥的思路看一遍concurrent包。小哥的文章主要是用法,我就主要看源码了。BlockingQueue同步的FIFO容器,主要方法: 实现有五种:ArrayBlockingQueue、DelayQueue、LinkedBlockingQueue、PriorityBlockingQueue、Synchron原创 2017-03-29 17:58:57 · 507 阅读 · 0 评论 -
[造轮子]Android动态加载框架总结
用了一周多,做了一个Android动态加载的小玩具DCommand。支持下载APK,获取其中的资源、执行代码、启动Activity(这个是抄的,非常粗糙)。 最开始只是觉得动态加载逻辑代码很有用,如果MVP模式使用合理的话,对于大部分的逻辑更新、线上bug修复直接使用动态下发APK,更新P端的逻辑即可。后来越来越复杂,最后基本所有方面都可以动态使用,如果再深入开发的话,做个MVP框架也是可以的(当原创 2016-02-25 20:27:57 · 998 阅读 · 0 评论 -
由Looper引发的crash及Looper源代码笔记
Crash项目线上有一个crash,Exception与此相同。但出问题的原因经过分析,并不是多线程操作Adapter导致的,而是androidannotation的@UIThread标签导致的。 @UIThread实际上是给MainLooper post了一个Runnable,如果有两个都是@UIThread的函数嵌套调用,如: @UIThread void notifyChange()原创 2015-10-22 11:26:43 · 559 阅读 · 0 评论 -
[源码]MultiDex
判断每个dex的新旧使用SharedPreferences存时间戳和crc来决定是否更新,其实就是用一个生命周期与dex文件相同的位置去存储数据就好这个CRC是全局的CRC,减少了计算量所有secondary dex输出为zip文件,这样是为了保持和DexClassLoader和DexPathList的兼容反射是扩展了DexClassLoader中的dex入口,与一般的动态加载不太一样原创 2016-04-12 11:23:01 · 454 阅读 · 0 评论 -
[源码]Gson
尽量泛化,记录一下Gson大大小小合理的设计和编码方式。合理设计原创 2016-04-21 20:41:01 · 809 阅读 · 0 评论 -
[源码]Choreographer
协调展示的基础类是ThreadLocal的,所有的run,都是在本Looper中frame间隔是10ms不是16ms,避免掉帧使用DisplayEventReceiver同步vSync独立的final Object作为锁对于单次任务队列,最快的实现是用链表,使用时直接通过修改next将队列分割成两个“`CallbackRecord callbacks = mHead;原创 2015-12-01 14:38:59 · 650 阅读 · 0 评论 -
一种用 Proxy 解决继承依赖的方法
一种用 Proxy 解决继承依赖的方法问题思路解决遗留问题问题在项目拆分的过程中,一定会遇到依赖问题。有一些代码非常细节,不适合作为对外接口暴露给上层,而上层很可能需要继承自这些类。例如,App 级别的 WebViewClient 的封装。作为业务 common 层的代码,包含了极多的业务逻辑,并不应该放到 api 包中。但是,一定存在某些特殊页面需要创建一个有特殊逻辑的 WebViewCl...原创 2018-10-10 18:59:28 · 480 阅读 · 0 评论 -
[造轮子]一个关于IOC初始化的失败脑洞
问题所有IOC系统,都不可避免的要进行实现的注册,包括很多初始化相关的事情。在Android上,随便一个多module的App,多多少少都有相同的问题。 Android冷启动App,IOC系统启动时,基本都要反射来突破Module间依赖的限制(如果这个能解决,也就不需要IOC了)。此时,性能一定会有一些问题,而且理解上不太容易描述清楚。解决方法提高性能的方法有不少种:每个M...原创 2018-02-13 18:28:38 · 305 阅读 · 0 评论 -
[源码]TextView源码
提起TextView,脑子里想着用起来应该是很简单的,然而作为显示文字的所有控件的基类,想要完全挖掘出TextView的能力,还是很复杂的。最近做一个需求,要在限制长度的输入框里识别粘贴的淘口令,因为对TextView了解太肤浅,bug无数,特意看一下源码学习一下(听iOS同学说,各个平台的对外接口都比较接近,这也是一个认知文字系统的好方法)。 主要关注TextView对外暴露的set接口,以及原创 2018-01-18 16:24:25 · 980 阅读 · 0 评论 -
用Annotation简化Preference存储
现状有很多Preference来自于某些对象的字段,这些字段的存储其实非常繁琐,每增加一个字段,需要修改3个地方:key对象字段对象内容的存储目标是搞成单点修改,但是:受限于java的Annotation限制很多,对于泛型、继承支持不太好,很难跟Preference的能力对应上不太想做AnnotationProcessor最后定成两点修改:定义enum作为key定义annotati原创 2017-09-29 14:30:48 · 361 阅读 · 0 评论 -
H5预加载的实现
预加载说小了就是个提前load,说大了,就是HybridApp的最基础功能。 Html5官方有个prefetch的attribute,用来做页面间的prefetch。其实在native跳h5容器的过程中更需要这种流程,否则很容易导致体验劣化。 其实方案蛮多的:直接下载url + WebView#loadDataWithBaseURL 优点是简单,缺点就是只能预加载下个页面的html内容,这样原创 2017-08-01 11:04:46 · 6402 阅读 · 0 评论 -
GUI架构方法
某个大神写的UI设计模式的综述类文章,笔记如下:MVC分为两层Domain层和Presentation层,前者负责通用数据的CRUD和逻辑,后者负责展示。对象分为两类:域(Domain)数据对象和显示数据对象。域对象与显示完全无关。Model是内存的Bean不是SQL中的行。数据绑定时,没有全局控制器协调多个View,而是使用Observer模式,View直接在Model中监听变化,进而更新原创 2015-09-10 17:25:55 · 1304 阅读 · 0 评论 -
Theme读取的工具类
用TypedArray读Theme很麻烦,很机械。可以用annotation来搞定。 public static void fillObject(Context context, Object object) { Class clazz = object.getClass(); ResIds ids = (ResIds) clazz.getAnnotation(ResIds.cla原创 2017-08-15 16:00:33 · 279 阅读 · 0 评论 -
Fragment生命周期的奇怪设定
线上发生了一个神奇的问题:fragment在onCreate的时候初始化数据,判断异常并finishActivity。然而居然走到了onViewCreated… 原因是Fragment的生命周期的调用关系跟臆想的不一样。在FragmentManager内部,Fragment会有几个[状态](http://grepcode.com/file/repo1.maven.org/maven2/com.go原创 2017-08-16 11:04:51 · 313 阅读 · 0 评论 -
Animator源码
做百分比的定时更新,发现用Handler.postDelay会卡,同样的逻辑放到Animator里就不会。拜读一下Animator是怎么做的。 主要是四个类:Animator(基类)、ValueAnimator(主要分析)、ObjectAnimator和AnimatorSet。Animator:Animator是不做线程同步的,所有方法都是口头要求同线程操作。Handler的postDelay是原创 2015-11-25 20:40:13 · 599 阅读 · 0 评论 -
Android雷达图变种的一个实现
遇到需求,要做一个雷达图类似的图。大概就是一个正n边型,每个顶点有一个View,多边形外接圆圆心有一个View。原创 2016-06-21 19:51:47 · 703 阅读 · 0 评论 -
[造轮子]Android多线程下载
初以为,下载是个极其简单的东西,想试一下。因为知道某些app的下载失败率很高,所以搞了个小聪明讨个巧,分块下载,每块一个md5,如果分块校验失败,则对本块重新下载(貌似古时候的FlashGet就是这么搞的)。模块理想情况下,还是分层的:对外接口:为使用下载功能暴露的接口,启停、取消之类的系统接口:监听系统事件控制下载过程下载:执行下载的部分日志:记录下载的状态,保证下载可以在中断后恢复存储原创 2016-06-13 17:40:51 · 615 阅读 · 0 评论 -
谷歌官方建议笔记——ANR、JNI
原文UI 5s没响应,BroadcastReceiver 10s未完成都是ANR如果运行时间会很长,用IntentService替代BroadcastReceiver一旦无响应时间超过100ms,用户就会感觉卡。如果在某个页面需要耗时的更新,那么分块的更新数据,及时进行展示———原创 2015-07-20 19:51:25 · 678 阅读 · 0 评论 -
由LaunchMode引发的问题
在做来往分享的时候,遇到了一个奇葩的问题。 我们的app(Foo)由一个LauncherActivity(L)启动,L在启动MainActivity(M)之后finish自己。Scheme也统一由L接收,并转发至M。其中,M是singleTask的。 当通过Foo分享到来往之后,点击通过Scheme启动Foo,此时会出现L的闪屏页,但是不会留在M。点开Foo,发现已经打开了Scheme相原创 2015-07-23 18:05:11 · 759 阅读 · 0 评论 -
谷歌官方建议笔记——多线程
原文对于多核机器,应使用多线程对任务进行并行化在Runnable启动时,调用android.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_BACKGROUND);设置线程优先级,避免过多的线程切换在Runnable通过Thread.currentThread()获得当前线程,以及时停止线程(个人觉得没什么用,re原创 2015-07-20 17:16:53 · 907 阅读 · 0 评论 -
谷歌官方建议笔记——多线程
原文不得不说一句,谷歌口气好大,SMP啊…怎么着也是超算领域的名词啊…Android上的处理器主要分为两种:uni-processor,流水线级的并行;SMP,内核级的并行Android处理器保证,读与读之间不会重排序,写与写之间不会重排序即便是写通的Cache,在真正数据落地前也会运行数条指令对现有的大部分ARM处理器来说,32bytes的数据读写基本上是在一个Cache Line,是原子原创 2015-07-25 16:27:39 · 609 阅读 · 0 评论 -
Sticky Header的另一种实现方法
使用Section Indexer的list单个item一般情况下使用的数据结构是 {data:"what's inside", category:"section name"} 这样存储其实是浪费了很多的空间,因为category的名字被存储的多次。在移动环境中,传输这种多余信息是不文明的。 由此可以演化出两种数据结构,一个是树形的{category0:[data...data],...};原创 2015-05-12 19:06:29 · 1235 阅读 · 0 评论 -
Fragment笔记和源码阅读
官方说明为了自动恢复Fragment状态,Fragment需要有(三选一): idtag容器有idFragmentTransaction 是一个标准的Command模式,将transaction压栈,供后续back时进行revert操作,不调用addToBackStack将会导致Fragment的引用被释放commit不是立即执行,而是向UI Handler post了一个runnabl原创 2015-05-13 10:11:09 · 535 阅读 · 0 评论 -
Deep Link
官方说明 基本上就是利用scheme跳转实现web(特别是搜索结果)对App的调用。App端要加入对http页面的filter,filter要有 <category android:name="android.intent.category.BROWSABLE" /> 然后在传入的intent中得到相应的数据就行了。被搜索端(web)需要让Google看到一个对于activity的描述翻译 2015-05-11 12:03:31 · 534 阅读 · 0 评论 -
android编程 完全退出程序的方法总结
<br />1<br />在2.2之前的系统 api4-7中 有一个restartPackage()函数<br />ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);<br />am.restartPackage(getPackageName());<br />需要permission<br /><uses-permission android:name="android.permission.原创 2010-10-24 09:43:00 · 1832 阅读 · 0 评论 -
图片加边框
有一个需求是在不确定形状的原创 2014-07-10 13:10:25 · 635 阅读 · 0 评论 -
谷歌官方建议笔记——性能
原文尽量减少对象的创建,从而减少GC次数。包括:减少不必要的中间变量:包括函数局部变量、返回值等对于String,最好使用substring,此时新的String是原始数据的子集的引用int比Integer要快对于一个Bean的数组,可以转变为多个基本类型的数组的集合,减少对象的创建,可以参考ArrayMap如果不需要访问对象的成员变量,尽量使用static方法。会有15%-25%的性能提原创 2015-09-17 20:20:10 · 561 阅读 · 0 评论 -
谷歌官方建议笔记——内存
原文所有进程都是由Zygote fork出来的,所以大部分内存分页都是在进程间共享的Dalvik code、app resources、so文件都是放到mmap里面的,能适应原创 2015-09-17 20:39:31 · 647 阅读 · 0 评论 -
谷歌官方建议笔记——布局
原文layout_weight会measure两次ImageView+TextView可以使用Compound Drawable代替如果FrameLayout仅作为容器出现,merge会更高效,FrameLayout本身并没有任何控制位置的能力,只有背景和Padding超过10层会非常严重的性能问题include Layout时,可以使用layout_*属性覆盖被include的Layou原创 2015-09-17 20:56:40 · 531 阅读 · 0 评论 -
使用LocalBroadcast实现跨Activity的MVVM
问题工作中遇到了一个问题: 封装了一个Activity组,这组Activity执行了相类似的业务A,但是少部分文案、图片是有差别的,而且要求在这组Activity执行的过程中,后台运行的其他业务可以随时(或在业务A回调时)修改这些显示内容。 不优雅的方案有: - 回调中传递Activity的引用。这样限制了修改时机 - 在某单例中注册当前Activity,同时在Activity上暴露相应的修原创 2016-05-06 20:53:04 · 1585 阅读 · 0 评论 -
关于Android键盘遮挡
事件应对软键盘遮挡的问题,可以处理四个不同的事件,事件和调用顺序如下: - onSizeChanged(Activity需要是AdjustResize的) - onLayout(不用监听onMeasure,回调的位置太多了) - addOnLayoutChangeListener监听layout的回调事件 - getViewTreeObserver().addOnGlobalLayoutL原创 2016-03-24 14:15:21 · 2079 阅读 · 0 评论 -
LocalBroadcastManager源码
代码官方使用的DCL单例并没有使用volatile,看样子关系不大使用的是Handler+MainLooper,所有调用都是在UIThread注册是synchronized,线程安全对ArrayList进行删除时,从后向前比较,效率会高一点点为了避免对同一个Intent的多次广播,在匹配一次后,会给filter置位,后续不进行匹配,全部结束后进行重置(line:200)。貌似比不置位用Ar原创 2015-08-06 20:12:56 · 448 阅读 · 0 评论