前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >android中使用sqlite、复制assets下的数据库到SD卡、支持大于1M的文件

android中使用sqlite、复制assets下的数据库到SD卡、支持大于1M的文件

作者头像
战神伽罗
发布2019-07-24 15:56:08
1.2K0
发布2019-07-24 15:56:08
举报
文章被收录于专栏:Eureka的技术时光轴

初学android,达人忽略,欢迎扔石头.

android中使用sqlite、复制assets下的数据库到SD卡、支持大于1M的文件

如果使用SD卡,需要在AndroidManifest.xml中设置权限

代码语言:javascript
复制
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"></uses-permission>
代码语言:javascript
复制
package cn.arthur.common;
 import java.io.File;
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
 import android.content.Context;
 import android.database.sqlite.SQLiteDatabase;
 import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.database.sqlite.SQLiteException;
import android.database.sqlite.SQLiteOpenHelper;
/**
 * @author Joshua
 * 用法:
 * DBHelper dbHelper = new DBHelper(this);
 * dbHelper.createDataBase();
 * SQLiteDatabase db = dbHelper.getWritableDatabase();
 * Cursor cursor = db.query()
 * db.execSQL(sqlString);
 * 注意:execSQL不支持带;的多条SQL语句,只能一条一条的执行,晕了很久才明白
 * 见execSQL的源码注释 (Multiple statements separated by ;s are not supported.)
 * 将把assets下的数据库文件直接复制到DB_PATH,但数据库文件大小限制在1M以下
 * 如果有超过1M的大文件,则需要先分割为N个小文件,然后使用copyBigDatabase()替换copyDatabase()
 */
public class DBHelper extends SQLiteOpenHelper {
    //用户数据库文件的版本
    private static final int DB_VERSION    = 1;
    //数据库文件目标存放路径为系统默认位置,cn.arthur.examples 是你的包名
    private static String DB_PATH        = "/data/data/cn.arthur.examples/databases/";
/*
    //如果你想把数据库文件存放在SD卡的话
    private static String DB_PATH        = android.os.Environment.getExternalStorageDirectory().getAbsolutePath()
                                        + "/arthurcn/drivertest/packfiles/";
*/
    private static String DB_NAME         = "hello.db";
    private static String ASSETS_NAME     = "hello.db";
    private SQLiteDatabase myDataBase    = null;
    private final Context myContext;
     /** 
      * 如果数据库文件较大,使用FileSplit分割为小于1M的小文件
      * 此例中分割为 hello.db.101    hello.db.102    hello.db.103
      */
    //第一个文件名后缀
    private static final int ASSETS_SUFFIX_BEGIN    = 101;
    //最后一个文件名后缀
    private static final int ASSETS_SUFFIX_END        = 103;
    
    /**
     * 在SQLiteOpenHelper的子类当中,必须有该构造函数
     * @param context    上下文对象
     * @param name        数据库名称
     * @param factory    一般都是null
     * @param version    当前数据库的版本,值必须是整数并且是递增的状态
     */
    public DBHelper(Context context, String name, CursorFactory factory, int version) {
        //必须通过super调用父类当中的构造函数
        super(context, name, null, version);
        this.myContext = context;
    }
    
    public DBHelper(Context context, String name, int version){
        this(context,name,null,version);
    }
    public DBHelper(Context context, String name){
        this(context,name,DB_VERSION);
    }
    
    public DBHelper (Context context) {
        this(context, DB_PATH + DB_NAME);
    }
    
    public void createDataBase() throws IOException{
        boolean dbExist = checkDataBase();
        if(dbExist){
            //数据库已存在,do nothing.
        }else{
            //创建数据库
            try {
                File dir = new File(DB_PATH);
                if(!dir.exists()){
                    dir.mkdirs();
                }
                File dbf = new File(DB_PATH + DB_NAME);
                if(dbf.exists()){
                    dbf.delete();
                }
                SQLiteDatabase.openOrCreateDatabase(dbf, null);
                // 复制asseets中的db文件到DB_PATH下
                copyDataBase();
            } catch (IOException e) {
                throw new Error("数据库创建失败");
            }
        }
    }
    
    //检查数据库是否有效
    private boolean checkDataBase(){
        SQLiteDatabase checkDB = null;
        String myPath = DB_PATH + DB_NAME;
        try{            
            checkDB = SQLiteDatabase.openDatabase(myPath, null, SQLiteDatabase.OPEN_READONLY);
        }catch(SQLiteException e){
            //database does't exist yet.
        }
        if(checkDB != null){
            checkDB.close();
        }
         return checkDB != null ? true : false;
    }
 
    /**
     * Copies your database from your local assets-folder to the just created empty database in the
     * system folder, from where it can be accessed and handled.
     * This is done by transfering bytestream.
     * */
    private void copyDataBase() throws IOException{
        //Open your local db as the input stream
        InputStream myInput = myContext.getAssets().open(ASSETS_NAME);
        // Path to the just created empty db
        String outFileName = DB_PATH + DB_NAME;
        //Open the empty db as the output stream
        OutputStream myOutput = new FileOutputStream(outFileName);
        //transfer bytes from the inputfile to the outputfile
        byte[] buffer = new byte[1024];
        int length;
        while ((length = myInput.read(buffer))>0){
            myOutput.write(buffer, 0, length);
        }
        //Close the streams
        myOutput.flush();
        myOutput.close();
        myInput.close();
    }
    
    //复制assets下的大数据库文件时用这个
    private void copyBigDataBase() throws IOException{
        InputStream myInput;
        String outFileName = DB_PATH + DB_NAME;
        OutputStream myOutput = new FileOutputStream(outFileName);
        for (int i = ASSETS_SUFFIX_BEGIN; i < ASSETS_SUFFIX_END+1; i++) {
            myInput = myContext.getAssets().open(ASSETS_NAME + "." + i);
            byte[] buffer = new byte[1024];
            int length;
            while ((length = myInput.read(buffer))>0){
                myOutput.write(buffer, 0, length);
            }
            myOutput.flush();
            myInput.close();
        }
        myOutput.close();
    }
    
    @Override
    public synchronized void close() {
        if(myDataBase != null){
            myDataBase.close();
        }
        super.close();
    }
    
    /**
     * 该函数是在第一次创建的时候执行,
     * 实际上是第一次得到SQLiteDatabase对象的时候才会调用这个方法
     */
    @Override
    public void onCreate(SQLiteDatabase db) {
    }
    
    /**
     * 数据库表结构有变化时采用
     */
    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    }
}

how copy database from assets to ExternalStorage?

代码语言:javascript
复制
public class MainActivity extends Activity {

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    File f1=new File(Environment.getExternalStorageDirectory(),"aaa");
    f1.mkdir();
    InputStream in = null;
    try {
        Toast.makeText(getBaseContext(), "error", Toast.LENGTH_LONG).show();
        in = getBaseContext().getAssets().open("home");
    } catch (IOException e) {
        // TODO Auto-generated catch block
        Toast.makeText(getBaseContext(), "error", Toast.LENGTH_LONG).show();
        e.printStackTrace();
    }
    OutputStream ou = null;
    try {
        ou = new FileOutputStream(Environment.getExternalStorageDirectory()+"aaa"+ "/"+"home" );
    } catch (FileNotFoundException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    try {
        CopyDB(in, ou);
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
}
public void CopyDB(InputStream in, OutputStream ou) throws IOException
{
    byte []buffer=new byte[1024];
    int length;
    while((length=in.read(buffer))>0)
    {
        try {
            ou.write(buffer, 0, length);
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        }
    in.close();
    ou.close();

}

https://stackoverflow.com/questions/26870624/how-copy-database-from-assets-to-externalstorage

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
数据库
云数据库为企业提供了完善的关系型数据库、非关系型数据库、分析型数据库和数据库生态工具。您可以通过产品选择和组合搭建,轻松实现高可靠、高可用性、高性能等数据库需求。云数据库服务也可大幅减少您的运维工作量,更专注于业务发展,让企业一站式享受数据上云及分布式架构的技术红利!
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档