如何理解在主线程进行读写操作而导致ANR?

刚看了一篇优秀博文,讲了导致ANR的原因之一是CPU满负荷,可能是因为在主线程频繁的文件读写。我想问的问题是为什么在子线程执行文件读写就不会CPU满负荷?难道主线程执行的占用时间比子线程长?

简单来说,就是导致anr的原因是失去响应,而不是cpu负载
放在ui线程,会导致界面阻塞,失去响应
放在子线程里,ui线程本身不操作,还能响应,因此就不会失去响应
但是放在ui线程还是子线程,cpu的占用是一样的,不存在放在子线程就不消耗cpu了
最后,你看的文章是错的。不要抱着那个错误的文章纠结了。“优秀博文”并不代表文章就不是错的,那个只是编辑根据访问量推荐出来的。

你看到的文章的作者概念不清,anr = Application Not Responding,翻译成中文叫做应用失去响应,注意是没有响应,而不是cpu满载。
也就是说,界面线程不能响应用户的操作了,卡死了。
先不论读写文件会不会造成cpu满负荷(实际上不会),子线程造成造成cpu满负荷,但是只要界面线程还能处理用户响应,那么就不会导致anr
而主线程如果正在做同步的操作,而阻塞了用户操作,哪怕没有cpu满负荷,也会造成anr,因此主线程要避免长时间处理同步的代码,这才是问题的关键。

那么导致ANR的根本原因是什么呢?简单的总结有以下两点:
1.主线程执行了耗时操作,比如数据库操作或网络编程
2.其他进程(就是其他程序)占用CPU导致本进程得不到CPU时间片,比如其他进程的频繁读写操作可能会导致这个问题。

那么如何避免ANR的发生呢或者说ANR的解决办法是什么呢?
1.避免在主线程执行耗时操作,所有耗时操作应新开一个子线程完成,然后再在主线程更新UI。
2.BroadcastReceiver要执行耗时操作时应启动一个service,将耗时操作交给service来完成。
3.避免在Intent Receiver里启动一个Activity,因为它会创建一个新的画面,并从当前用户正在运行的程序上抢夺焦点。如果你的应用程序在响应Intent广 播时需要向用户展示什么,你应该使用Notification Manager来实现。

子线程执行文件读写不会CPU满负荷吗?
换个专用的服务器,服务器会优化多任务,不让某个进程占大量CPU。

NIO读写文件、读写混合
NIO是面向缓冲、双向通道的--可以写、也可以读;可以设置为异步。

主线程一般来说不建议进行太多操作,毕竟他要用来响应事件,如果你把操作都放到主线程,他就没有时间去响应从而导致ANR