Ist bei einer Android-App etwas falsch an der folgenden Vorgehensweise?
public class MyApp extends android.app.Application {
private static MyApp instance;
public MyApp() {
instance = this;
}
public static Context getContext() {
return instance;
}
}
und ihn überall dort übergeben (z.B. SQLiteOpenHelper), wo Kontext benötigt wird (und natürlich nicht durchsickert)?
23 Stimmen
Nur um dies für andere zu verdeutlichen, können Sie dann die
<application>
Knoten Ihrer AndroidManifest.xml-Datei, um die folgende Attributdefinition aufzunehmen:android:name="MyApp"
. MyApp muss sich unter demselben Paket befinden, auf das Ihr Manifest verweist.0 Stimmen
Warum die Statik? Die Anwendungsinstanz ist immer vor allen anderen geschaffen. Wo immer Sie auf den Anwendungskontext zugreifen sollen, wird er Ihnen als Argument übergeben. Dieser Ansatz kann Ihre Tests verkomplizieren. Static-itis fördert die allgemeine Kopplung.
6 Stimmen
AWESOME Weg, um das Problem der Bereitstellung eines Kontextes an den SQLiteOpenHelper zu umgehen! Ich habe ein Singleton "SQLiteManager" implementiert und war bei "wie zum Teufel bekomme ich einen Kontext zu dem Singleton?" stecken.
8 Stimmen
Nur damit Sie wissen, dass Sie Ihre Anwendung über eine ihrer Superschnittstellen zurückgeben. Wenn Sie also zusätzliche Methoden innerhalb von MyApp bereitstellen würden, könnten Sie diese nicht verwenden. Ihre getContext() sollte stattdessen einen Rückgabetyp von MyApp haben, und auf diese Weise können Sie später hinzugefügte Methoden sowie alle Methoden in ContextWrapper und Context verwenden.
5 Stimmen
Siehe auch goo.gl/uKcFn - es ist eine weitere Antwort auf einen ähnlichen Beitrag. Besser setzen Sie die statische Variable in onCreate und nicht c'tor.
0 Stimmen
Hat bei mir super funktioniert :) Thankx alex & Matt Hyuggins
0 Stimmen
Dies wird nicht funktionieren, wenn Ihr SQLiteOpenHelper von einem Content Provider verwendet wird, da das onCreate() des Content Providers vor dem onCreate() der Anwendung aufgerufen wird.
0 Stimmen
@MattHuggins Wenn mein Paketname com.example.xyz ist, kann ich ihn unter dem Anwendungsknoten wie folgt definieren: Android:name="com.example.xyz.MyApp" oder einfach Android:name="MyApp".
0 Stimmen
@yanchenko: Haben Sie das Szenario getestet, bei dem die GC Ihre Anwendung beendet? Würde Ihre Lösung dann noch funktionieren? Der Grund für meine Frage ist, dass es in Android Szenarien gibt, in denen eine Anwendung nach einem
Context
um bestimmte Aufgaben zu erledigen. Zum Beispiel das Abhören von Lautstärkeänderungen, die durch die Hardware-Lautstärketasten ausgelöst werden. Ich nehme an, dass in diesem Fall, wenn die App bereits von der GC beendet wurde, es keineContext
zur Verfügung steht, gibt es? Die einzige Lösung wäre dann, auf Null zu prüfenContext
und angemessen zu reagieren.1 Stimmen
@ChuongPham Wenn das Framework Ihre Anwendung beendet hat, gibt es nichts, was auf den Null-Kontext zugreift...
0 Stimmen
Ich glaube, Sie wollen anrufen
super()
von Ihrem Konstruktor.0 Stimmen
FWIW, für alle, die mit
Xamarin
Bei Android ist dies eingebaut alsglobal::Android.App.Application.Context
.