Ich lerne gerade über Cursor in Android in Bezug auf eine SQLite-Datenbank. Ich habe die folgende Methode, die pet Informationen aus einem Tierheim-Datenbank abruft und zeigt es auf einem einfachen Textview:Wie verhindert das Schließen eines Cursors in Android Speicherlecks?
private void displayDatabaseInfo() {// Erstellen und/oder öffnen Sie eine Datenbank aus, es zu lesen SQLiteDatabase db = mDbHelper.getReadableDatabase();
// Perform query Cursor cursor = db.query(PetEntry.TABLE_NAME, null, null, null, null, null, null); TextView displayView = (TextView) findViewById(R.id.text_view_pet); try { displayView.setText("The pets table contains " + cursor.getCount() + " pets.\n\n"); displayView.append(PetEntry._ID + " - " + PetEntry.COLUMN_PET_NAME + " - " + PetEntry.COLUMN_PET_BREED + " - " + PetEntry.COLUMN_PET_GENDER + " - " + PetEntry.COLUMN_PET_WEIGHT + "\n"); // Figure out the index of each column int idColumnIndex = cursor.getColumnIndex(PetEntry._ID); int nameColumnIndex = cursor.getColumnIndex(PetEntry.COLUMN_PET_NAME); int breedColumnIndex = cursor.getColumnIndex(PetEntry.COLUMN_PET_BREED); int genderColumnIndex = cursor.getColumnIndex(PetEntry.COLUMN_PET_GENDER); int weightColumnIndex = cursor.getColumnIndex(PetEntry.COLUMN_PET_WEIGHT); // Iterate through all the returned rows in the cursor while (cursor.moveToNext()) { // Use that index to extract the String or Int value of the word // at the current row the cursor is on. int currentID = cursor.getInt(idColumnIndex); String currentName = cursor.getString(nameColumnIndex); String currentBreed = cursor.getString(breedColumnIndex); int currentGender = cursor.getInt(genderColumnIndex); int currentWeight = cursor.getInt(weightColumnIndex); // Display the values from each column of the current row in the cursor in the TextView displayView.append("\n" + currentID + " - " + currentName + " - " + currentBreed + " - " + currentGender + " - " + currentWeight); } } finally { cursor.close(); } }
Ich verstehe einfach nicht, warum wir den Cursor schließen müssen. Die Lektion sagt, es ist, um Speicherlecks zu vermeiden, aber das Cursor-Objekt ist eine lokale Variable innerhalb der Methode und wäre Garbage Collectable, nachdem die Methode beendet ist. Warum müssen wir immer noch close() anrufen?
Ich habe ein wenig recherchiert und mir auch andere Fragen und Antworten angeschaut. Dieser gibt einen Hinweis: A few questions about SQLite database cursors in Android. Es heißt
oder close() es selbst. Wenn Sie dies nicht tun, wird der Speicher auslaufen, der GC hilft nicht dabei, da hinter dem Cursor native Ressourcen stehen (z. B. Dateizugriffe auf die Datenbank).
So kann ich sehen, dass der Müllsammler nicht genug ist. Aber ich verstehe es noch nicht gut. Kann jemand mit diesen nativen Ressourcen zusammenarbeiten und warum die Garbage Collection nicht ausreicht? Danke im Voraus.