Android上下文没有活动?还有其他没有活动的节目?

bob*_*bob 15 gps android location android-context android-activity

我会尽力把它变成一个全面的问题:

我正在编写一个方法来获取一个包含Android设备城市名称的String,由LocationManagerand getLastKnownLocation()和所有这些确定.

然后我意识到我需要在另一个活动中再次做同样的事情,那么为什么不在LocationFinder我的程序中创建一个完全独立的类(),而不是在任何地方编写重复的代码?

但是我遇到了困扰我的问题.例如,如果我创建这个类(LocationFinder),它是否应该扩展Activity,即使它实际上从未可视化?所有这些类会做的是有各种样的吸气剂getLastKnownCity()getCurrentCity()与返回字符串.我假设它不会扩展Activity类,因为它实际上不是一个活动.

但是接下来我用什么Context:

Geocoder geocoder = new Geocoder(Context context, Locale locale)
Run Code Online (Sandbox Code Playgroud)

这让我认为它必须是一项活动.所以我扩展了Activity,并用构造函数替换了

@Override
protected void onCreate(..............
Run Code Online (Sandbox Code Playgroud)

但出于某种原因,即使我放了,也永远不会被召唤

String city = new LocationFinder().getLastKnownCity();
Run Code Online (Sandbox Code Playgroud)

我的第一行LocationFinderonCreate()

System.out.println("HEY!")
Run Code Online (Sandbox Code Playgroud)

它甚至都没有达到目的.我得到一个空指针android.internal.os.LoggingPrintStream.println()和其他东西.

另外,还有一堆来自Activity类的系统常量.例如,我需要得到LOCATION_SERVICE,这是一个String,如果不扩展Activity,我就无法获得.当然,我可以作弊,只是放入文字字符串,但这感觉不对.

Ale*_*ier 21

编辑:如果可能的话,使用frogmanx的答案.这只应在他的答案无法使用时使用.(即直接需要背景的单身人士.)

听起来你应该扩展Application而不是Activity.

使您的应用程序像这样:

public class MyApplication extends Application {
    private static MyApplication instance;

    public MyApplication() {
        instance = this;
    }

    public static MyApplication getInstance() {
         return instance;
    }
Run Code Online (Sandbox Code Playgroud)

然后将此属性添加到清单的应用程序标记:

 <application android:name=".your.package.MyApplication" ... />
Run Code Online (Sandbox Code Playgroud)

毕竟,你可以MyApplication.getInstance()从任何地方打电话来获得一个上下文.

  • 令人敬畏的+1恰好是我的情况,单身人士需要一个上下文.花了我很多年才找到这个! (2认同)

fro*_*anx 13

在构造类时,您可以拥有一个构造函数,该构造函数接受Context并在类中为其指定一个本地Context对象.

public class LocationFinder {
     private Context myContext;
     private Geocoder geocoder;

     public LocationFinder(Context context)
     {
         myContext = context;
         geocoder = new Geocoder(myContext);
     }

}
Run Code Online (Sandbox Code Playgroud)

然后当您尝试访问此类时,请确保将其初始化为:

public class TestActivity extends Activity {
     protected void onCreate(Bundle savedInstanceState)
     {
          super.onCreate(savedInstanceState);
          setContentView(R.layout.main);
          LocationFinder lFinder = new LocationFinder(getApplication());
     }
}
Run Code Online (Sandbox Code Playgroud)

当然,您无法从将要运行的每个类访问上下文.因此,对View的引用就足够了.

LocationFinder lFinder = new LocationFinder(anyView.getApplication());
Run Code Online (Sandbox Code Playgroud)


Sim*_*mon 5

should it extend Activity, even though it is never actually visualized?
Run Code Online (Sandbox Code Playgroud)

否。来自Android 文档

活动是用户可以做的一件专注的事情。几乎所有活动都与用户交互,因此Activity类负责为您创建一个窗口,您可以在其中放置setContentView(View)的UI。

将活动视为用户看到的屏幕。

但是接下来我要为Geocoder geocoder使用什么上下文= new Geocoder(Context context,Locale locale)

Activity类扩展Context,因为做了很多其他类包括的Application上下文提供对与扩展上下文的类关联的资源的访问。

在需要与活动相关联的资源以及由具体活动类实现的方法进行交互时,您仅需要并且仅应使用活动上下文。当确实需要对该上下文的访问权限时,您可以将其传递给需要访问的类,通常作为该类的构造函数的参数。

如果您确实在扩展它的活动之外传递了一个活动上下文,请确保引用的范围和生命周期小于或等于扩展活动,否则如果该活动由于垃圾而被破坏,则会泄漏大量内存收集器无法释放内存,因为存在对上下文的引用。

如果您了解一下Geocoder的构造函数,就会知道,它以Context作为参数。有一个线索说明为什么需要上下文:

     Geocoder(Context context, Locale locale)
Constructs a Geocoder whose responses will be localized for the given Locale.  [1]: 
Run Code Online (Sandbox Code Playgroud)

要求使用Context的原因是为了获得有关平台语言环境和当前系统语言环境的系统信息。

因此,在您的示例中,您可以简单地将Application上下文传递给构造函数,您可以使用 getApplicationContext()

例如,我需要到达LOCATION_SERVICE,它是一个字符串,如果不扩展Activity则无法获得

您可以从应用程序上下文中获取它。