从非活动单例类获取应用程序上下文

Posted

技术标签:

【中文标题】从非活动单例类获取应用程序上下文【英文标题】:Get application context from non activity singleton class 【发布时间】:2014-03-16 03:33:43 【问题描述】:

在我的 android 项目中,我有 ImageAdapter 类,我在其中传递应用程序上下文以满足进一步的需求。

public class ImageAdapter extends BaseAdapter 
    private Context c;

    public ImageAdapter(Context c) 
            this.c = c;
    
    ...

问题是我想让 ImageAdapter 成为一个单例,以便从我的所有活动中轻松访问此类的实例。但我不知道如何将应用程序上下文从我的一项活动的 getApplicationContext() 方法传递到 ImageAdapter。那么有没有什么“魔法”可以做到以下几点?

public class ImageAdapter extends BaseAdapter 

    private Context c;

    private static class Holder 
            public static final ImageAdapter IA = new ImageAdapter();
    

    private ImageAdapter() 
            this.c = /* some magic here */.getApplicationContext();
    

    public static ImageAdapter getInstance() 
            return Holder.IA;
    
    ...

也许你有一些其他的想法来分享我的任何活动的 ImageAdapter。 我是 android 的新手,我对在活动之间传递数据的方式有点困惑。

如果有任何帮助,我将不胜感激。

【问题讨论】:

您在问题中说“我想让 ImageAdapter 成为单例,以便从我的所有活动中轻松访问此类的实例。”您如何轻松访问 imageadapter 类的实例并使用你们所有的活动,请详细说明我想增加我对它的了解 【参考方案1】:

更新:2018 年 3 月 6 日

使用MyApplication 实例而不是Context 实例。 Application 实例本身就是一个单例上下文实例。

public class MyApplication extends Application 

    private static MyApplication mContext;

    @Override
    public void onCreate() 
        super.onCreate();
        mContext = this;
    

    public static MyApplication getContext() 
        return mContext;
    

上一个答案

您可以像这样获取应用程序上下文:

public class MyApplication extends Application 

    private static Context mContext;

    @Override
    public void onCreate() 
        super.onCreate();
        mContext = getApplicationContext();
    

    public static Context getContext() 
        return mContext;
    

然后,您可以从方法MyApplication.getContext()调用应用程序上下文

不要忘记在清单文件中声明应用程序:

<application
    android:name=".MyApplication"
    android:icon="@drawable/icon"
    android:label="@string/app_name" >

【讨论】:

顺便说一句,应用程序应用程序上下文; getApplicationContext() 可以替换为 this。 (getApplicationContext 存在,因此如果您有 any 上下文,则可以访问应用程序。)代码没有错,只是指出这一点。 不建议将 Android 上下文类放在静态字段中。静态字段会泄漏上下文——Android Studio 也会警告这个问题。 这个答案是否仍然是最新的?因为编译器说“不要将 Android 上下文类放在静态字段中;这是内存泄漏(也会破坏 Instant Run) @JimClermonts 我知道自从您提出问题以来答案已经更新,但更新后的答案不应给出任何警告。不同之处在于Context 可以是任何上下文,包括活动(不时被销毁)。通过指定它是 Application 对象(只要应用程序存在)就不应该有任何问题 这仍然是真实的吗?【参考方案2】:

我宁愿将上下文实例作为参数传递给单例中真正需要它的每个方法

【讨论】:

没办法,我需要覆盖方法中的上下文 @Override public View getView(int position, View convertView, ViewGroup parent) 据我所知它会自动触发。【参考方案3】:

方法 #1:

由于您指定 ImageAdapter 是单例,一个简单的答案是从可以访问应用上下文的类创建该单例:

public class MyApplication extends Application 
    @Override
    public void onCreate() 
        super.onCreate();
        ImageAdapter.createIt(this);
    


public class ImageAdapter extends BaseAdapter 
    private static ImageAdapter it;
    // Get the singleton.
    public static ImageAdapter getIt() 
        return it;
    
    // Call this once, to create the singleton.
    public static void createIt(Context context) 
        it = new ImageAdapter(context);
    

    private final Context c;
    private ImageAdapter(Context context) 
        c = context;
    


方法 #2:

如果不是单例,那么我会使用接受的答案。在这种情况下,请从 ImageAdapter 中删除局部变量,因为始终可以从 MyApplication 获取上下文。扩展已接受的答案,如果您想要一个方便的本地方法,请定义 ImageAdapter.getContext()。完整的解决方案:

public class MyApplication extends Application 
    private static Context appContext;
    public static Context getContext() 
        return appContext;
    

    @Override
    public void onCreate() 
        super.onCreate();
        appContext = this;
    


public class ImageAdapter extends BaseAdapter 
    public ImageAdapter() 
    

    // [Optional] Call this whenever you want the app context.
    private Context getContext() 
        return MyApplication.getContext();
    

【讨论】:

以上是关于从非活动单例类获取应用程序上下文的主要内容,如果未能解决你的问题,请参考以下文章

从非活动类中获取上下文

请问java 单例类 与 静态类 有何不同?

必须在不同的活动中调用单例 socketIO 类?

什么时候/为什么我的Java单例实例被销毁?

32单例类

正确处理Android上的Realm实例