如何将SQLite数据库嵌入到应用程序中?

Rob*_*uch 30 sqlite import android

我想我有一些基本的理解问题,所以也许有人能够提供帮助:-)

我正在使用Eclipse开发一个Android应用程序,这个应用程序将使用一个数据库(只能从数据库中读取).该数据库包含大约4,000个条目,即不能通过源代码创建和填充数据库.因此,我已事先创建了数据库及其所有记录.

但是,如何将此数据库文件"嵌入"到我的应用程序中然后访问它?数据库的文件大小约为500 kB.从远程服务器下载也不是一种选择,因为这是不允许的.

谢谢,罗伯特

Ant*_*nko 27

我解决了这个问题:

  1. 添加file.db到project/assets文件夹中;

  2. 写下一堂课:

    public class LinnaeusDatabase extends SQLiteOpenHelper{
    
        private static String DATABASE_NAME = "Dragonfly.db";
        public final static String DATABASE_PATH = "/data/data/com.kan.linnaeus/databases/";
        private static final int DATABASE_VERSION = 1;
    
        private SQLiteDatabase dataBase;
        private final Context dbContext;
    
        public LinnaeusDatabase(Context context) {
            super(context, DBActivity.DatabaseName, null, DATABASE_VERSION);
            this.dbContext = context;
            DATABASE_NAME = DBActivity.DatabaseName;
            // checking database and open it if exists
            if (checkDataBase()) {
                openDataBase();
            } else
            {
                try {
                    this.getReadableDatabase();
                    copyDataBase();
                    this.close();
                    openDataBase();
    
                } catch (IOException e) {
                    throw new Error("Error copying database");
                }
                Toast.makeText(context, "Initial database is created", Toast.LENGTH_LONG).show();
            }
        }
    
        private void copyDataBase() throws IOException{
            InputStream myInput = dbContext.getAssets().open(DATABASE_NAME);
            String outFileName = DATABASE_PATH + DATABASE_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();
        }
    
        public void openDataBase() throws SQLException {
            String dbPath = DATABASE_PATH + DATABASE_NAME;
            dataBase = SQLiteDatabase.openDatabase(dbPath, null, SQLiteDatabase.OPEN_READWRITE);
        }
    
        private boolean checkDataBase() {
            SQLiteDatabase checkDB = null;
            boolean exist = false;
            try {
                String dbPath = DATABASE_PATH + DATABASE_NAME;
                checkDB = SQLiteDatabase.openDatabase(dbPath, null,
                SQLiteDatabase.OPEN_READONLY);
            } catch (SQLiteException e) {
                Log.v("db log", "database does't exist");
            }
    
            if (checkDB != null) {
                exist = true;
                checkDB.close();
            }
            return exist;
        }
    }
    
    Run Code Online (Sandbox Code Playgroud)


evi*_*one 14

关于在Android应用程序中使用自己的SQLite数据库的 ReignDesign博客上的精彩文章.基本上你预先创建你的数据库,把它放在你的apk资产目录中,并首先使用复制到"/ data/data/YOUR_PACKAGE/databases /"目录.


Ste*_*roy 10

我在过去通过在res/raw资源中的应用程序中存储JSON文件然后在第一次加载时加载文件来完成此操作.从那里,您可以使用批量插入模式批量导入条目.有关此技术的示例,请参阅我的数据库加载程序.该res/raw风格的一个好处是您可以使用Android资源选择系统将数据本地化到不同的区域,因此您可以为不同的语言或区域使用不同的数据库(或其中的一部分).

您还可以将原始SQL转储放在类似的文件中,并在第一次加载时加载它.您可以使用openRawResource(int)从资源中获取文件.我建议这样做,而不是存储预先制作的sqlite数据库文件,以增加sqlite版本之间的兼容性,以及使数据库维护更容易(从应用程序开发生命周期POV).

批量加载时,请确保使用事务,因为这有助于加快速度并使加载更加可靠.

  • 是的,这可能会有问题.在您的情况下,如果您希望以不仅仅是sqlite数据库的格式存储它,那么将它存储为SQL可能是有意义的.我想知道在创建数据库时,有多少问题与二进制/版本兼容性有关. (2认同)

Sur*_*gch 5

在对此答案的评论中,CommonsWare建议使用@evilone在此处提出的相同方法(即,从资产自己复制数据库)。相反,您应该使用久经考验的产品SQLiteAssetHelper。我已经在Android Studio中使用过它,并且效果很好。

方向比较明确。以下是一些主要摘录:

如果您正在使用Gradle构建系统,只需在build.gradle文件中添加以下依赖项:

dependencies {
    compile 'com.readystatesoftware.sqliteasset:sqliteassethelper:+'
}
Run Code Online (Sandbox Code Playgroud)

SQLiteAssetHelper像通常那样扩展SQLiteOpenHelper,为构造函数提供数据库名称和版本号:

public class MyDatabase extends SQLiteAssetHelper {

    private static final String DATABASE_NAME = "northwind.db";
    private static final int DATABASE_VERSION = 1;

    public MyDatabase(Context context) {
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
    }
}
Run Code Online (Sandbox Code Playgroud)

将数据库放入assets/databases/northwind.db(使用您拥有的任何数据库名称)。

该数据库第一次被使用 getReadableDatabase()或被getWritableDatabase()调用。