在扩展SQLiteOpenHelper的DatabaseHelper类中,我设置了各种方法将Cursors返回到其他活动,这样我就不会在除DatabaseHelper之外的任何其他类中执行任何查询。在那些方法中,我之后不关闭Cursor或数据库,并返回它:
public Cursor getCoursesLeft()
{
// Open a readable database.
SQLiteDatabase database = this.getReadableDatabase();
// Query the database and return the cursor.
return database.query(DEGREE_PLAN_TABLE, null, DEGREE_COLUMN_TAKEN + " = ?",
new String[] { "0" }, null, null, DEGREE_COLUMN_CLASS_NAME + " COLLATE NOCASE");
}
从我调用该方法的Activity中,我确保关闭使用它后返回的Cursor。
由于Cursor是一个Object,它应该通过引用传递,对吗?因此,从其他Activity关闭它应关闭原始对象,如果我理解正确关闭Cursor也会关闭数据库。
这是一个糟糕的编码习惯吗?
似乎是随机的我会得到一个LogCat错误,说在数据库中从未调用过close,我在代码中找到的唯一可能是我在这些方法中返回游标的原因。
答案 0 :(得分:1)
如果我理解正确关闭光标也会关闭 数据库中。
这听起来不太对劲。您必须在关闭所有游标后明确关闭数据库。 logcat错误是由于您没有关闭数据库并可能尝试打开它的另一个实例。
顺序很重要,首先是游标,然后是数据库实例。
<bad joke in 3.. 2.. 1...>
其余的听起来不是什么不好的做法,当你得db它你只需要db它。 :d
[编辑] :你说你做到了这一点:
public Cursor getCoursesLeft()
{
// Open a readable database.
SQLiteDatabase database = this.getReadableDatabase();
^^^ here you're creating a new instance of the db
which means the db is opened for reading, and the scope of this variable
is lost outside this function. This means you can not close this instance explicitly
// Query the database and return the cursor.
return database.query(DEGREE_PLAN_TABLE, null, DEGREE_COLUMN_TAKEN + " = ?",
new String[] { "0" }, null, null, DEGREE_COLUMN_CLASS_NAME + " COLLATE NOCASE");
}
而是有一个数据库变量,你可以在这个方法之外访问,并在你完成光标处理后关闭它(并且你已经关闭了光标)
SQLiteDatabase database;
public Cursor getCoursesLeft()
{
// Open a readable database.
database = this.getReadableDatabase();
// Query the database and return the cursor.
return database.query(DEGREE_PLAN_TABLE, null, DEGREE_COLUMN_TAKEN + " = ?",
new String[] { "0" }, null, null, DEGREE_COLUMN_CLASS_NAME + " COLLATE NOCASE");
}
public void someOtherFunction() {
Cursor blah = getCoursesLeft();
// do something with blah
blah.close();
database.close();
}
答案 1 :(得分:0)
不关闭游标只会导致内存泄漏。关闭数据库是不同的。
关闭游标就像关闭创建游标时生成的某些.file
文件的特定连接。
因此你应始终关闭光标。
这是不好的编码?
不,是的。不要让你的Activity乱用那些临时文件。虽然什么都不会发生,但这似乎并不好看