项目开发中,个人贪图简便,在Activity的生命周期里使用了一个全局的布尔静态变量,而正是因为这个举动,差点导致版本转测block,在此记录以警醒自己(项目细节不谈)
原因探析
Intent bindIntent = new Intent(context, BindActivity.class);
bindIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
bindIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
bindIntent.putExtra(AUTO_BIND, bean.isbAutoBind());
context.startActivity(bindIntent);
项目中使用了上述代码去启动一个BindActivity。当服务端发来一个Bind消息时(自定义的TCP消息),这段代码就会被程序执行。而Bind消息发送的次数取决于用户的操作行为,也就是说,这个Bind消息是可以发送多次的。
当第一次BindActivity已经呈现出来以后,此时内存驻留了其实例对象ActivityA,之后又收到一个Bind消息,由于使用了FLAG_ACTIVITY_NEW_TASK和FLAG_ACTIVITY_CLEAR_TOP的启动模式,此时在内存中又会创建出一个BindActivity实例ActivityB。
当ActivityB要覆盖ActivityA时,我们知道,这两个Activity会各自执行自己的生命周期流程,如下:
ActivityA-onPause()->ActivityB-onCreate()->ActivityB-onStart()->ActivityB-onResume()->ActivityA-onStop()->ActivityA-onDestroy()
悲催的是,在BindActivity的onCreate和onDestroy方法里面,执行了如下代码
public static boolean sIsRegistered = false;
protected void onCreate(Bundle savedInstanceState) {
...
sIsRegistered=true;
...
}
protected void onDestroy() {
...
sIsRegistered=false;
...
}
我们知道,静态变量在全局只有一份实例,且只初始化一次,其生命周期与程序的生命周期一致,这样就导致在ActivityB->onCreate方法里面该静态变量被设置成true后,又马上被ActivityA->onDestroy()方法设置成了false。这并不是期望得到的结果,也就导致了一些重要的问题(细节这里不透露)。
因此,写下这篇文章,用来警醒自己,日后不要再犯同样错误,同时,也想将个人的教训分享给广大读者,希望你们也可以有所收获。