我刚刚发现我的应用程序保持崩溃时,我调用了我的数据库类中的getWritableDatabase()
方法。以下是我的代码:
主要活动:
package com.google.assignment_lab;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import com.google.assignment_lab.database.UserTable;
public class MainActivity extends AppCompatActivity implements View.OnClickListener{
Button mainRegisterButton, mainLoginButton;
UserTable userTable = new UserTable(this);
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mainRegisterButton = findViewById(R.id.mainRegisterButton);
mainLoginButton = findViewById(R.id.mainLoginButton);
mainRegisterButton.setOnClickListener(this);
mainLoginButton.setOnClickListener(this);
}
@Override
public void onClick(View view) {
Intent intent;
if(view == mainRegisterButton){
intent = new Intent(this, RegisterActivity.class);
startActivity(intent);
}
if(view == mainLoginButton){
intent = new Intent(this, LoginActivity.class);
startActivity(intent);
}
}
}
UserTable.java:
package com.google.assignment_lab.database;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import androidx.annotation.Nullable;
public class UserTable extends SQLiteOpenHelper {
public static String DATABASE_NAME = "MyData";
public static int DATABASE_VERSION = 1;
public static String TABLE_NAME = "Users";
Context context;
SQLiteDatabase database;
public UserTable(@Nullable Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
this.context = context;
database = getWritableDatabase();
database = getReadableDatabase();
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
String query = "CREATE TABLE IF NOT EXISTS " + TABLE_NAME + " (username TEXT, password TEXT, email TEXT, phone TEXT)";
sqLiteDatabase.execSQL(query);
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
}
}
我尝试删除getWritableDatabase()和getReadableDatabase(),应用程序工作正常。但问题是,我的用户表从未创建为onCreate方法。我该如何解决这个问题?
错误日志:
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.google.assignment_lab, PID: 8732
java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{com.google.assignment_lab/com.google.assignment_lab.MainActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'java.io.File android.content.Context.getDatabasePath(java.lang.String)' on a null object reference
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3551)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3782)
at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:101)
at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2307)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loopOnce(Looper.java:201)
at android.os.Looper.loop(Looper.java:288)
at android.app.ActivityThread.main(ActivityThread.java:7872)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:548)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:936)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'java.io.File android.content.Context.getDatabasePath(java.lang.String)' on a null object reference
at android.content.ContextWrapper.getDatabasePath(ContextWrapper.java:380)
at android.database.sqlite.SQLiteOpenHelper.getDatabaseLocked(SQLiteOpenHelper.java:370)
at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase(SQLiteOpenHelper.java:316)
at com.google.assignment_lab.database.UserTable.<init>(UserTable.java:20)
at com.google.assignment_lab.MainActivity.<init>(MainActivity.java:16)
at java.lang.Class.newInstance(Native Method)
at android.app.AppComponentFactory.instantiateActivity(AppComponentFactory.java:95)
at androidx.core.app.CoreComponentFactory.instantiateActivity(CoreComponentFactory.java:45)
at android.app.Instrumentation.newActivity(Instrumentation.java:1339)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3538)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3782)
at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:101)
at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2307)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loopOnce(Looper.java:201)
at android.os.Looper.loop(Looper.java:288)
at android.app.ActivityThread.main(ActivityThread.java:7872)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:548)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:936)
2条答案
按热度按时间insrf1ej1#
我不知道你为什么要把
getWritableDatabase()
和getReadableDatabase()
赋值给同一个变量。我最近也在使用DbHandlers,根据我的经验,我通常创建**单独的方法 *(在本地定义)***用于阅读和获取数据:-示例:-
还有这个
旁注;***不要***添加
db.close()
,如果你确定你会多次调用这些方法。omqzjyyz2#
问题是您在
SQLiteOpenHelper
子类的构造函数中调用getWritableDatabase()
,这个构造函数在调用onCreate()
之前发生,所以数据库还没有创建。相反,您应该在代码的另一部分调用
getWriteableDatabase()
,例如在Activity或Fragment中创建SQLiteOpenHelper
的示例。顺便说一句,我建议你看看API,这是一个非常强大的数据库访问库,这是一种现代的访问方式。