在开发过程中,我们多多少少都遇到过应用崩溃的情况,这里总结一些常见的崩溃问题,可以帮助减少一些开发中出现的问题
DialogFragment 使用 dismiss 关闭弹窗
在开发中,我们常常使用 DialogFragment
显示弹窗。如果你使用了 DialogFragment
,那么你就需要注意使用 DialogFragment
的 dismissAllowingStateLoss
而不是 dismiss
方法。
这是因为,当使用dismiss
方法来关闭DialogFragment
时,在某些情况下可能会导致Activity
状态丢失异常 java.lang.IllegalStateException,因此如果没有保存状态的需要,更推荐使用 dismissAllowingStateLoss
来关闭弹窗。
Fragment 使用 commit 来显示
在 Android 中,提供了 commit
、 commitNow
、commitAllowingStateLoss
和 commitNowAllowingStateLoss
四种方法来执行事务操作。它们的作用如下:
方法 | 作用 |
---|---|
commit | 将一个Fragment 事务添加到FragmentManager 的事务队列中,但不会立即执行,会等待线程准备好后才执行事务。该方法不能在Activity 的onSaveInstanceState 方法之后调用,否则会抛出异常 |
commitNow | 不同于 commit 方法,该方法会立即执行事务。但是该方法不能在Activity 的onSaveInstanceState 方法之后调用,否则会抛出异常 |
commitAllowingStateLoss | 和commit 方法作用一致,不同的是该方法允许状态丢失,可以在onSaveInstanceState 方法之后调用,并且不会抛出异常 |
commitNowAllowingStateLoss | 和 commitNow 方法作用一样,不同的是该方法允许状态丢失,可以在onSaveInstanceState 方法之后调用,并且不会抛出异常 |
从上面的表格可以看出,除非需要保存状态,否则不推荐使用 commit
和 commitNow
方法。
Bitmap 创建
在开发过程中,我们常常使用 Bitmap。这里需要注意使用 Bitmap
的 create 方法或者 BitmapFactory
的 decodeXXX 方法来创建一个 Bitmap 对象时可能会抛出异常。因此建议使用 runCatching
来确保异常的处理。
runCatching {
Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888)
}
除了 Bitmap 创建需要注意之外,我们使用 Bitmap 前还需要判断是否被回收。
first 和 last 和 get
在 kotlin 的集合扩展函数中,我们可以很简单的通过 first
、last
、get
方法来分别获取第一个、最后一个和指定位置的值。但是一旦获取不到指定的值,这些方法就会抛 NoSuchElementException
异常,导致应用崩溃
为了避免这些可能的崩溃情况,建议使用 firstOrNull
、lastOrNull
、getOrNull
、 getOrElse
方法来代替上面方法。
文件长度太长
在 Android 中,文件名长度一般有一定限制,通常最大长度在 255 个字符左右。如果文件名的长度超过了最大的长度会抛出异常,造成程序崩溃。
除以0
在开发过程中,我们不可避免的会使用到除法,这时就需要注意除数是不能为0的。我们可以在使用除法前,提前判断,也可以使用 coerceAtLeast
方法来确保最小值大于0。
val result = a / b.coerceAtLeast(1)
使用Glide前,先判断页面是否回收
由于 Glide 加载图片是异步操作,当界面被destory后,这个网络请求刚好成功了,这时调用Glide.with就会发生 You cannot start a load for a destroyed activity
错误。解决方法是在调用Glide.with前先判断,代码如下:
service?.fetchUserProfile(id) { result, errMsg, icon ->
if (result == 200) {
if (context is FragmentActivity) {
if ((context as FragmentActivity).isFinishing || (context as FragmentActivity).isDestroyed) {
return
}
}
Glide.with(context)
.load(icon)
.into(view)
}
}
Csense - Kotlin Checked Exceptions
最后推荐一个发现可能抛出异常的插件 Csense - Kotlin Checked Exceptions,当你使用一个可能抛出异常的方法时,这个插件会显示图标提示,非常方便。