在阅读文档之前,如果插入不成功,我希望SQLiteDatabase的insertOrThrow()
方法抛出异常。
但是,documentation表示insertOrThrow()
方法
返回新插入行的行ID,如果发生错误则返回 -1
那么,如果在发生错误时它返回-1
,它会在什么情况下抛出异常?
答案 0 :(得分:3)
我的理解是,如果所有代码都可以正确执行并且发生“EXPECTED”错误,它将返回-1。但是,并非所有错误/异常都得到处理,并且仍可能触发一些异常:
HERE您可以找到insert()
和insertOrThrow()
的实施。
您可以看到两种方法都相似。但是,insert()
会为您处理SQLException
。 insertOrThrow()
不会处理任何异常,您应该自己动手。
public long insert(String table, String nullColumnHack, ContentValues values) {
try {
return insertWithOnConflict(table, nullColumnHack, values, CONFLICT_NONE);
} catch (SQLException e) {
Log.e(TAG, "Error inserting " + values, e);
return -1;
}
}
public long insertOrThrow(String table, String nullColumnHack, ContentValues values)
throws SQLException {
return insertWithOnConflict(table, nullColumnHack, values, CONFLICT_NONE);
}
两种方法调用insertWithOnConflict()
,其实现为HERE:
public long insertWithOnConflict(String table, String nullColumnHack,
ContentValues initialValues, int conflictAlgorithm) {
acquireReference();
try {
// CODE
try {
// ONLY HERE I return some value.... Otherwise, I'll raise an exception
return statement.executeInsert();
} finally {
statement.close();
}
} finally {
releaseReference();
}
}
在实现中,只有当statement.executeInsert();
返回某些内容时才会看到它返回“-1”(并且似乎“-1”来自此处):
... /框架/碱/核心/ JNI / android_database_SQLiteConnection.cpp
static jlong nativeExecuteForLastInsertedRowId(JNIEnv* env, jclass clazz,
jlong connectionPtr, jlong statementPtr) {
SQLiteConnection* connection = reinterpret_cast<SQLiteConnection*>(connectionPtr);
sqlite3_stmt* statement = reinterpret_cast<sqlite3_stmt*>(statementPtr);
int err = executeNonQuery(env, connection, statement);
return err == SQLITE_DONE && sqlite3_changes(connection->db) > 0
? sqlite3_last_insert_rowid(connection->db) : -1;
}
如果中间发生任何其他错误/异常,则会抛出异常。
如果您遵循被调用的方法,则可以看到未处理其他错误。此外,您会注意到SQLite实际上将由C任务(而不是Java)执行。因此,仍然可能发生一些非预期的错误。
答案 1 :(得分:0)
您可以查看SQLiteDatabase source code以查看其工作原理。如果SQL字符串无效,它似乎会抛出SQLiteDatabaseCorruptException,否则返回-1。
答案 2 :(得分:-1)
insertOrThrow()方法抛出异常并返回-1。通过这种方式,您可以检查您的查询是否成功。如果它返回-1你的行动没有完成,你需要弄清楚出了什么问题!