0

将预先存在的数据库复制到新创建的数据库后,我收到错误消息,该数据库用于填充带有标题的列表视图。这一切都很好,但是一旦我滚动列表视图,我就会收到关于数据库未关闭的错误。

我不知道在哪里放置 close 声明。我已经在我的活动超类的 onDestroy() 方法中使用,并在每次使用游标填充用于列表视图的数组时打开和关闭数据库。

我在这里查看了其他问题,但我似乎无法找到这个特定问题的答案。

非常感谢

继承人logcat:

12-11 12:55:58.072: E/Database(17830): close() was never explicitly called on database  '/data/data/com.sil.android.bofseg2012/databases/bofsegdb1' 
12-11 12:55:58.072: E/Database(17830): android.database.sqlite.DatabaseObjectNotClosedException: Application did not close the cursor or database object that was opened here
12-11 12:55:58.072: E/Database(17830):  at android.database.sqlite.SQLiteDatabase.<init>(SQLiteDatabase.java:1810)
12-11 12:55:58.072: E/Database(17830):  at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:817)
12-11 12:55:58.072: E/Database(17830):  at com.sil.android.bofseg2012.DBHelper.openDatabase(DBHelper.java:108)
12-11 12:55:58.072: E/Database(17830):  at com.sil.android.bofseg2012.DBHelper.getDatabase(DBHelper.java:121)
12-11 12:55:58.072: E/Database(17830):  at com.sil.android.bofseg2012.GamesList.<init>(GamesList.java:55)
12-11 12:55:58.072: E/Database(17830):  at com.sil.android.bofseg2012.ContentsActivity.populateLists(ContentsActivity.java:49)
12-11 12:55:58.072: E/Database(17830):  at com.sil.android.bofseg2012.ContentsActivity.onResume(ContentsActivity.java:102)
12-11 12:55:58.072: E/Database(17830):  at android.app.Instrumentation.callActivityOnResume(Instrumentation.java:1149)
12-11 12:55:58.072: E/Database(17830):  at android.app.Activity.performResume(Activity.java:3823)

这是我的 dbOpenHelper 类:

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import android.content.ContentValues;
import android.content.Context;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

public class DBHelper extends SQLiteOpenHelper
{
    private static final String DB_PATH = "/data/data/com.sil.android.bofseg2012/databases/";
    private static final String DB_NAME = "bofsegdb1";
    private static final int VERSION = 1;
    private static final String TABLE_NAME = "bofseg_full_1";
    protected static final String SEARCHABLE_TABLE = "searchable_table";
    private static final String KEY_ID = "_id";
    private static final String GAME_NAME = "game_name";
    private static final String PLAYERS = "players";
    private static final String VENUE = "venue";
    private static final String DURATION = "duration";
    private static final String EQUIPMENT = "equipment";
    private static final String SECTION = "section";
    private static final String FAVES = "fave";
    private SQLiteDatabase myDB;
    private final Context dbContext;

    public DBHelper(Context context)
    {
        super(context, DB_NAME, null, VERSION);
        this.dbContext=context; 
    }

    // check the imported database exists
    private boolean checkDatabase()
    {
        File dbFile = new File(DB_PATH + DB_NAME);
        boolean dbExists = dbFile.exists();
        return dbExists;
    }

    private void createAndCopyDataBase() throws IOException
    {
        if(!this.checkDatabase())
        {
            try
            {
                this.getWritableDatabase();

            } catch (Exception e1)
            {
                System.out.println("Error creating system db");
                e1.printStackTrace();
            }

            try
            {
                this.copyDatabase();
                //System.out.println("db copied");
            }catch(IOException e)
            {
                throw new Error("Error copying database");
            }
            finally
            {
                try
                {
                    this.close();
                } catch (Exception e)
                {               
                    e.printStackTrace();
                }
            }
            System.out.println("DB created and copied  and closed successfully");
        }
    }


    private void copyDatabase() throws IOException
    {
            InputStream myInput = dbContext.getAssets().open(DB_NAME);
            String outFileName = DB_PATH + DB_NAME;
            OutputStream myOutput = new FileOutputStream(outFileName);
            byte[] buffer = new byte[1024];
            int length;
            while((length = myInput.read(buffer))>0)
            {
                myOutput.write(buffer,0,length);
            }
            myOutput.flush();
            myOutput.close();
            myInput.close();        

            this.createVirtualTable();
            this.getDatabase().execSQL("INSERT INTO " + SEARCHABLE_TABLE  + " SELECT * FROM " + TABLE_NAME);
            this.close();

    }

    public void openDatabase() throws SQLException
    {
        String sysDBPath = DB_PATH + DB_NAME;
            // this is line 108 that is throwing the error:
        this.myDB = SQLiteDatabase.openDatabase(sysDBPath, null, SQLiteDatabase.OPEN_READWRITE);
        System.out.println("DBH openDatabase myDB is open = " + this.myDB.isOpen());
    }

    public SQLiteDatabase getDatabase()
    { 
        try
        {
            this.createAndCopyDataBase();
        } catch (IOException e)
        {
            e.printStackTrace();
        }
        this.openDatabase();

        return this.myDB;
    }

    private void createVirtualTable()
    {
        try
        {
            this.getDatabase().execSQL("CREATE VIRTUAL TABLE ["+SEARCHABLE_TABLE+"] USING fts3 (" +
                    "[" +KEY_ID+"] TEXT," +
                    "[" +GAME_NAME+"] TEXT," +
                    "[" +PEOPLE+"] TEXT," +
                    "[" +VENUE+"] TEXT," +
                    "[" +DURATION +"] TEXT," +
                    "[" +EQUIPMENT +"] TEXT," +
                    "[" +SECTION +"] TEXT," +
                    "[" +FAVES+"] TEXT," +");"
                    );
            System.out.println("virtual table created");
        }
        catch (Exception e)
        {
            e.printStackTrace();
            this.deleteSearchableDBStructure(this.getDatabase());
        }

    }

    private void deleteSearchableDBStructure(SQLiteDatabase database)
    {
        try
        {
            database.execSQL("DROP TABLE IF EXISTS ["+SEARCHABLE_TABLE+"];");
        } catch (SQLException e)
        {           
            e.printStackTrace();
        }
    }


    public synchronized void close()
    {
                try
                {
                    this.myDB.close();
                    super.close();
                    System.out.println("myDb is open = " + this.myDB.isOpen());
                } catch (Exception e)
                {
                    System.out.println("Error in DBHelper close()");
                    e.printStackTrace();
                }
    }

    //Update the faves column of the db at row pageNumber
    public boolean addFavourite(int pageNumber)
    {
        boolean addedOk = false;
        ContentValues args = new ContentValues();

        try
        {
            args.put(FAVES, "y");
            this.openDatabase();
            this.myDB.update(TABLE_NAME, args, KEY_ID + " = " + pageNumber , null);
            addedOk = true;
        } catch (SQLException e)
        {       
            e.printStackTrace();
        }
        finally{
            try
            {
                this.close();
            }
            catch (Exception e) {
                e.printStackTrace();
            }

        }
        return addedOk;
    }

    @Override
    public void onCreate(SQLiteDatabase db)
    {

    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion)
    {
    }


}
4

1 回答 1

0

我认为您在更新后将其保持打开状态。也许通过添加this.myDB.close();afteraddedOk = true;可能会有所帮助

于 2012-12-11T18:02:35.840 回答