android.database.sqlite.SQLiteCantOpenDatabaseException:未知错误(代码 14):无法打开数据库仍然无法解决问题
android.database.sqlite.SQLiteCantOpenDatabaseException: unknown error (code 14): Could not open database still unable to fix issue
这个问题已经有人问过了,但是按照很多人的步骤我仍然无法解决这个问题,请帮忙。
我还在清单文件中添加了权限
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
这里是 logcat 错误。
07-17 15:23:58.253 14526-14526/com.techmobile2.yogahome E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.techmobile2.yogahome, PID: 14526
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.techmobile2.yogahome/com.techmobile2.yogahome.SettingPage}: android.database.sqlite.SQLiteCantOpenDatabaseException: unknown error (code 14): Could not open database
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2417)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2480)
at android.app.ActivityThread.access0(ActivityThread.java:151)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1377)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:155)
at android.app.ActivityThread.main(ActivityThread.java:5725)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1030)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:825)
Caused by: android.database.sqlite.SQLiteCantOpenDatabaseException: unknown error (code 14): Could not open database
at android.database.sqlite.SQLiteConnection.nativeOpen(Native Method)
at android.database.sqlite.SQLiteConnection.open(SQLiteConnection.java:235)
at android.database.sqlite.SQLiteConnection.open(SQLiteConnection.java:219)
at android.database.sqlite.SQLiteConnectionPool.openConnectionLocked(SQLiteConnectionPool.java:468)
at android.database.sqlite.SQLiteConnectionPool.open(SQLiteConnectionPool.java:190)
at android.database.sqlite.SQLiteConnectionPool.open(SQLiteConnectionPool.java:182)
at android.database.sqlite.SQLiteDatabase.openInner(SQLiteDatabase.java:874)
at android.database.sqlite.SQLiteDatabase.open(SQLiteDatabase.java:854)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:752)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:727)
at com.readystatesoftware.sqliteasset.SQLiteAssetHelper.getReadableDatabase(SQLiteAssetHelper.java:264)
at com.techmobile2.yogahome.Database.YogaDB.getSettingMode**(YogaDB.java:21)**
at com.techmobile2.yogahome.SettingPage.onCreate**(SettingPage.java:41)**
at android.app.Activity.performCreate(Activity.java:6018)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1130)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2370)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2480)
at android.app.ActivityThread.access0(ActivityThread.java:151)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1377)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:155)
at android.app.ActivityThread.main(ActivityThread.java:5725)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1030)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:825)
这是 yogaDB.java 文件,我也会提到行号
public class YogaDB extends SQLiteAssetHelper {
private static final String DB_NAME = "yoga.db";
private static final int DB_VER=1;
public YogaDB(Context context) {
super(context, DB_NAME, null, DB_VER);
}
public int getSettingMode()
{
**SQLiteDatabase db = getReadableDatabase();** //THIS is line 21
SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
String[] sqlSelect = {"Mode"};
String sqlTable = "Setting";
qb.setTables(sqlTable);
Cursor c = qb.query(db,sqlSelect,null,null,null,null,null);
c.moveToFirst();
return c.getInt(c.getColumnIndex("Mode"));
}
public void saveSettingMode(int value)
{
SQLiteDatabase db = getReadableDatabase();
String query = "UPDATE Setting SET Mode = "+value;
db.execSQL(query);
}
这里是SettingPage.java,我还会提到行号
public class SettingPage extends AppCompatActivity {
Button btnSave;
RadioButton rdiEasy,rdiMedium,rdiHard;
RadioGroup rdiGroup;
YogaDB yogaDB;
ToggleButton switchAlarm;
TimePicker timePicker;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_setting_page);
//Init view
btnSave = (Button)findViewById(R.id.btnSave);
rdiGroup = (RadioGroup)findViewById(R.id.rdiGroup);
rdiEasy = (RadioButton)findViewById(R.id.rdiEasy);
rdiMedium = (RadioButton)findViewById(R.id.rdiMedium);
rdiHard = (RadioButton)findViewById(R.id.rdiHard);
switchAlarm = (ToggleButton)findViewById(R.id.switchAlarm);
timePicker = (TimePicker)findViewById(R.id.timePicker);
yogaDB = new YogaDB(this);
int mode = yogaDB.getSettingMode(); this is line 41
setRadioButton(mode);
//Event
btnSave.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
saveWorkoutMode();
}
});
}
private void saveWorkoutMode() {
int selectedID = rdiGroup.getCheckedRadioButtonId();
if(selectedID == rdiEasy.getId())
yogaDB.saveSettingMode(0);
else if(selectedID == rdiMedium.getId())
yogaDB.saveSettingMode(1);
else if(selectedID == rdiHard.getId())
yogaDB.saveSettingMode(2);
}
private void setRadioButton(int mode) {
if(mode == 0)
rdiGroup.check(R.id.rdiEasy);
else if(mode == 1)
rdiGroup.check(R.id.rdiMedium);
else if(mode == 2)
rdiGroup.check(R.id.rdiHard);
}
我的 sql 数据库文件名是 yoga.db
请帮我解决我的问题
问题: 大多数时候 SQLiteCantOpenDatabaseException 发生在您从多线程访问 sqlite 数据库时。假设您在一个线程中打开了数据库,并试图在另一个线程中访问数据库将导致 SQLiteCantOpenDatabaseException 异常。
解决方案:为你的 SQLiteOpenHelper 创建一个单例对象class,并始终对多个线程使用相同的实例。
示例:
DBHelper class:
public class DBHelper extends SQLiteOpenHelper {
private DBHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
public synchronized static DBHelper getInstance(Context context) {
if (dbHelper == null) {
dbHelper = new DBHelper(context);
}
return dbHelper;
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//...
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
//...
onCreate(sqLiteDatabase);
}
}
用法:
private static SQLiteDatabase database;
DBHelper dbHelper = DBHelper.getInstance(context);
if (database == null) {
database = dbHelper.getWritableDatabase();
}
注意:切勿自行关闭 SqliteDatabase 实例android系统会自动关闭。
这个问题已经有人问过了,但是按照很多人的步骤我仍然无法解决这个问题,请帮忙。 我还在清单文件中添加了权限
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
这里是 logcat 错误。
07-17 15:23:58.253 14526-14526/com.techmobile2.yogahome E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.techmobile2.yogahome, PID: 14526
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.techmobile2.yogahome/com.techmobile2.yogahome.SettingPage}: android.database.sqlite.SQLiteCantOpenDatabaseException: unknown error (code 14): Could not open database
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2417)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2480)
at android.app.ActivityThread.access0(ActivityThread.java:151)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1377)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:155)
at android.app.ActivityThread.main(ActivityThread.java:5725)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1030)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:825)
Caused by: android.database.sqlite.SQLiteCantOpenDatabaseException: unknown error (code 14): Could not open database
at android.database.sqlite.SQLiteConnection.nativeOpen(Native Method)
at android.database.sqlite.SQLiteConnection.open(SQLiteConnection.java:235)
at android.database.sqlite.SQLiteConnection.open(SQLiteConnection.java:219)
at android.database.sqlite.SQLiteConnectionPool.openConnectionLocked(SQLiteConnectionPool.java:468)
at android.database.sqlite.SQLiteConnectionPool.open(SQLiteConnectionPool.java:190)
at android.database.sqlite.SQLiteConnectionPool.open(SQLiteConnectionPool.java:182)
at android.database.sqlite.SQLiteDatabase.openInner(SQLiteDatabase.java:874)
at android.database.sqlite.SQLiteDatabase.open(SQLiteDatabase.java:854)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:752)
at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:727)
at com.readystatesoftware.sqliteasset.SQLiteAssetHelper.getReadableDatabase(SQLiteAssetHelper.java:264)
at com.techmobile2.yogahome.Database.YogaDB.getSettingMode**(YogaDB.java:21)**
at com.techmobile2.yogahome.SettingPage.onCreate**(SettingPage.java:41)**
at android.app.Activity.performCreate(Activity.java:6018)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1130)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2370)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2480)
at android.app.ActivityThread.access0(ActivityThread.java:151)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1377)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:155)
at android.app.ActivityThread.main(ActivityThread.java:5725)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1030)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:825)
这是 yogaDB.java 文件,我也会提到行号
public class YogaDB extends SQLiteAssetHelper {
private static final String DB_NAME = "yoga.db";
private static final int DB_VER=1;
public YogaDB(Context context) {
super(context, DB_NAME, null, DB_VER);
}
public int getSettingMode()
{
**SQLiteDatabase db = getReadableDatabase();** //THIS is line 21
SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
String[] sqlSelect = {"Mode"};
String sqlTable = "Setting";
qb.setTables(sqlTable);
Cursor c = qb.query(db,sqlSelect,null,null,null,null,null);
c.moveToFirst();
return c.getInt(c.getColumnIndex("Mode"));
}
public void saveSettingMode(int value)
{
SQLiteDatabase db = getReadableDatabase();
String query = "UPDATE Setting SET Mode = "+value;
db.execSQL(query);
}
这里是SettingPage.java,我还会提到行号
public class SettingPage extends AppCompatActivity {
Button btnSave;
RadioButton rdiEasy,rdiMedium,rdiHard;
RadioGroup rdiGroup;
YogaDB yogaDB;
ToggleButton switchAlarm;
TimePicker timePicker;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_setting_page);
//Init view
btnSave = (Button)findViewById(R.id.btnSave);
rdiGroup = (RadioGroup)findViewById(R.id.rdiGroup);
rdiEasy = (RadioButton)findViewById(R.id.rdiEasy);
rdiMedium = (RadioButton)findViewById(R.id.rdiMedium);
rdiHard = (RadioButton)findViewById(R.id.rdiHard);
switchAlarm = (ToggleButton)findViewById(R.id.switchAlarm);
timePicker = (TimePicker)findViewById(R.id.timePicker);
yogaDB = new YogaDB(this);
int mode = yogaDB.getSettingMode(); this is line 41
setRadioButton(mode);
//Event
btnSave.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
saveWorkoutMode();
}
});
}
private void saveWorkoutMode() {
int selectedID = rdiGroup.getCheckedRadioButtonId();
if(selectedID == rdiEasy.getId())
yogaDB.saveSettingMode(0);
else if(selectedID == rdiMedium.getId())
yogaDB.saveSettingMode(1);
else if(selectedID == rdiHard.getId())
yogaDB.saveSettingMode(2);
}
private void setRadioButton(int mode) {
if(mode == 0)
rdiGroup.check(R.id.rdiEasy);
else if(mode == 1)
rdiGroup.check(R.id.rdiMedium);
else if(mode == 2)
rdiGroup.check(R.id.rdiHard);
}
我的 sql 数据库文件名是 yoga.db 请帮我解决我的问题
问题: 大多数时候 SQLiteCantOpenDatabaseException 发生在您从多线程访问 sqlite 数据库时。假设您在一个线程中打开了数据库,并试图在另一个线程中访问数据库将导致 SQLiteCantOpenDatabaseException 异常。
解决方案:为你的 SQLiteOpenHelper 创建一个单例对象class,并始终对多个线程使用相同的实例。
示例:
DBHelper class:
public class DBHelper extends SQLiteOpenHelper {
private DBHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
public synchronized static DBHelper getInstance(Context context) {
if (dbHelper == null) {
dbHelper = new DBHelper(context);
}
return dbHelper;
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//...
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
//...
onCreate(sqLiteDatabase);
}
}
用法:
private static SQLiteDatabase database;
DBHelper dbHelper = DBHelper.getInstance(context);
if (database == null) {
database = dbHelper.getWritableDatabase();
}
注意:切勿自行关闭 SqliteDatabase 实例android系统会自动关闭。