【发布时间】:2016-12-07 14:30:42
【问题描述】:
我正在摆弄 Android 中的 db 访问,以了解事情是如何处理的。
我的 MainActivity.java 文件中有以下代码:
Log.v("test db acc", "start getApplicationContext test");
FileDbHelper dbHelper1 = new FileDbHelper(getApplicationContext());
SQLiteDatabase db1 = dbHelper1.getWritableDatabase();
Log.v("test db acc", "success getApplicationContext test");
Log.v("test db acc", "start getContext test");
FileProvider provider = new FileProvider();
provider.testDbAccess();
Log.v("test db acc", "success getContext test");
这是 provider.testDbAccess() 函数的定义:
FileDbHelper dbHelper2 = new FileDbHelper(getContext());
SQLiteDatabase db2 = dbHelper2.getWritableDatabase();
第一次尝试访问数据库成功,没有任何错误。如果DB不存在就创建,创建db1对象后我可以查询和写入数据。
当我尝试使用Context 获取可写数据库并返回getContext() 时,它只是以NullPointerException 失败。它甚至没有开始创建数据库。即使我删除了getApplicationContext() 测试行的代码,也会出现症状。
这里的问题是,我正在尝试编写代码以从FileProvider 的数据库中获取查询,但我无法从该文件访问getApplicationContext()(它只会引发编译器错误)。
如果我在 MainActivity.java 文件中完成所有过程,我没有错误(我知道这不好,我这样做只是为了测试目的)。
我的问题是:
- 我应该如何以及在什么情况下创建我的数据库?
- 为什么我不能使用来自
FileProvider的getApplicationContext()? - 我可以从创建数据库的另一个上下文访问数据库吗?据我所知,SQLite 数据库只是在应用程序自己的文件夹中的 android 文件系统中创建的一个文件。不同的
Contexts 有什么区别? - 为什么我不能在
FileProvider.java中创建一个由getContext()返回的Context的数据库?
--编辑--
这是错误的logcat:
08-02 16:03:55.628 7614-7614/com.permasse.apps.file.android E/AndroidRuntime: FATAL EXCEPTION: main
java.lang.RuntimeException: Unable to resume activity {com.permasse.apps.file.android/com.permasse.apps.file.android.MainActivity}: java.lang.NullPointerException
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2575)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2603)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2089)
at android.app.ActivityThread.access$600(ActivityThread.java:130)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1195)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:4745)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:511)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:786)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.NullPointerException
at com.permasse.apps.file.android.FileProvider.testDbAccess(FileProvider.java:120)
at com.permasse.apps.file.android.MainActivity.onResume(MainActivity.java:32)
at android.app.Instrumentation.callActivityOnResume(Instrumentation.java:1184)
at android.app.Activity.performResume(Activity.java:5082)
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:2565)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:2603)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2089)
at android.app.ActivityThread.access$600(ActivityThread.java:130)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1195)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:4745)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:511)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:786)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
at dalvik.system.NativeStart.main(Native Method)
这里是 FileProvider.java 的相关部分。原始代码包括查询生成器、uri 匹配器等。我简化了代码以隔离问题。
public class FileProvider extends ContentProvider {
private FileDbHelper dbHelper;
@Override
public boolean onCreate() {
dbHelper = new FileDbHelper(getContext());
return true;
}
public void testDbAccess() {
SQLiteDatabase db = dbHelper.getWritableDatabase(); //Line no 120
}
}
和 MainActivity.java
public class MainActivity extends AppCompatActivity{
@Override
protected void onResume() {
super.onResume();
FileProvider provider = new FileProvider();
provider.testDbAccess(); //Line no 32
}
}
【问题讨论】:
-
我不确定您要做什么,但是您可以将
context传递给FileProvider类...new FileProvider(getApplicationContext());并在方法中使用context而不是getContext(),您可以从继承具有它们的类的类中调用 getContext() 或 getApplicationContext() ,例如Activity否则您必须传递它 -
我基本上试图做的是创建一个提供程序,稍后将绑定到加载程序。我喜欢在提供程序类中创建一个数据库对象,它根本不起作用(使用 getContext 上下文)。在具有 getApplicationContext 上下文的 MainActivity 中,相同的代码可以正常工作。这对我来说很奇怪,因为在这个应用程序中,它似乎工作:github.com/udacity/Sunshine-Version-2/blob/sunshine_master/app/… line no: 142
-
你的
FileProvider上课extends ContentProvider吗? -
是的,确实如此。我什至实现了查询方法。
-
好的,现在对于空指针异常,您可以发布logcat吗?
标签: android nullpointerexception android-sqlite android-context