使用static修饰符跟踪对象实例

时间:2012-12-21 02:00:23

标签: java android static instance

我目前正在编写Android应用程序,而且我对何时使用静态方法/字段有更高层次的质疑。

我的应用程序跟踪不同活动的时间使用情况,每个活动都是一个类的实例。我需要一个可以返回此类的所有实例的方法。

在我的Activity类中放置一个静态方法/字段是不好的设计:

static ArrayList<Activity> allInstances;    
public static void addToComprehensiveList(Activity a) {
    if(allInstances == null)
        allInstances = new ArrayList<Activity>();
    allInstances.add(a);
}
public static ArrayList<Activity> getComprehensiveList() {
    return allInstances;
}

这里的设计选择是什么?

2 个答案:

答案 0 :(得分:3)

保持静态的实例列表是一件相当安全和正常的事情。当你将项目添加到列表时,主要的问题就在于它。

例如,如果Activity有一个非常重要的构造函数,它在启动时调用addToComprehensiveList(this),那么有时未完全初始化的对象位于可公开访问的列表中。如果您的程序是单线程的,那么这不是太危险 - 除非构造函数稍后抛出异常,在这种情况下,对象将以未完全初始化的状态保留在列表中。

一种安全的方法是在工厂方法中创建实例,该方法在创建对象后将对象添加到列表中。当然,如果没有子类,只需添加到列表作为构造函数中的最后一个语句就可以正常工作。

这里的另一个危险是getComprehensiveList()返回对其实例列表的引用,这意味着客户端代码可能正在修改该列表而不需要您的类知道。即使客户端只是遍历列表,如果在迭代期间创建一个新的Activity,也会得到商品化异常。更安全的方法是返回列表的副本。

答案 1 :(得分:-2)

根据我的经验,在这种情况下,在沉重的压力或记忆中使用:

static ArrayList<Activity> allInstances; 

不保证可用。 VM可以将其清空,这就是Singleton可能更安全的原因。