Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android 使用存放在存assets文件夾下的SQLite數據庫

Android 使用存放在存assets文件夾下的SQLite數據庫

編輯:關於Android編程

因為這次的項目需要自帶數據,所以就就把數據都放到一個SQLite的數據庫文件中了,之後把該文件放到了assets文件夾下面。一開始打算每次都從assets文件夾下面把該文件夾拷貝到手機的SD卡或者手機自身的存儲上之後再使用,後來考慮到每次都拷貝的話效率不高,並且如果涉及到對數據庫的修改操作的話拷貝之後數據就被恢復了。

因此就寫了該封裝,該封裝只是在第一次使用數據庫文件的時候把該文件夾拷貝到手機的/data/data/應用程序報名/database文件夾下,之後就直接從這個地方使用了。並且它允許你直接通過assets文件夾下的數據庫名稱來獲取SQLiteDatabase對象,這樣就極大的方便了你對數據庫的使用。

package com.jemsn.database;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.HashMap;
import java.util.Map;

import android.content.Context;
import android.content.SharedPreferences;
import android.content.res.AssetManager;
import android.database.sqlite.SQLiteDatabase;
import android.util.Log;

/**
 * This is a Assets Database Manager
 * Use it, you can use a assets database file in you application
 * It will copy the database file to "/data/data/[your application package name]/database" when you first time you use it
 * Then you can get a SQLiteDatabase object by the assets database file 
 * @author RobinTang
 * @time 2012-09-20
 * 
 * 
 * How to use:
 * 1. Initialize AssetsDatabaseManager
 * 2. Get AssetsDatabaseManager
 * 3. Get a SQLiteDatabase object through database file
 * 4. Use this database object
 * 
 * Using example:
 * AssetsDatabaseManager.initManager(getApplication());	// this method is only need call one time
 * AssetsDatabaseManager mg = AssetsDatabaseManager.getManager();	// get a AssetsDatabaseManager object
 * SQLiteDatabase db1 = mg.getDatabase("db1.db");	// get SQLiteDatabase object, db1.db is a file in assets folder
 * db1.???	// every operate by you want
 * Of cause, you can use AssetsDatabaseManager.getManager().getDatabase("xx") to get a database when you need use a database
 */
public class AssetsDatabaseManager {
	private static String tag = "AssetsDatabase"; // for LogCat
	private static String databasepath = "/data/data/%s/database"; // %s is packageName
	
	
	// A mapping from assets database file to SQLiteDatabase object
	private Map databases = new HashMap();
	
	// Context of application
	private Context context = null;
	
	// Singleton Pattern
	private static AssetsDatabaseManager mInstance = null;
	
	/**
	 * Initialize AssetsDatabaseManager
	 * @param context, context of application
	 */
	public static void initManager(Context context){
		if(mInstance == null){
			mInstance = new AssetsDatabaseManager(context);
		}
	}
	
	/**
	 * Get a AssetsDatabaseManager object
	 * @return, if success return a AssetsDatabaseManager object, else return null
	 */
	public static AssetsDatabaseManager getManager(){
		return mInstance;
	}
	
	private AssetsDatabaseManager(Context context){
		this.context = context;
	}
	
	/**
	 * Get a assets database, if this database is opened this method is only return a copy of the opened database
	 * @param dbfile, the assets file which will be opened for a database
	 * @return, if success it return a SQLiteDatabase object else return null
	 */
	public SQLiteDatabase getDatabase(String dbfile) {
		if(databases.get(dbfile) != null){
			Log.i(tag, String.format("Return a database copy of %s", dbfile));
			return (SQLiteDatabase) databases.get(dbfile);
		}
		if(context==null)
			return null;
		
		Log.i(tag, String.format("Create database %s", dbfile));
		String spath = getDatabaseFilepath();
		String sfile = getDatabaseFile(dbfile);
		
		File file = new File(sfile);
		SharedPreferences dbs = context.getSharedPreferences(AssetsDatabaseManager.class.toString(), 0);
		boolean flag = dbs.getBoolean(dbfile, false); // Get Database file flag, if true means this database file was copied and valid
		if(!flag || !file.exists()){
			file = new File(spath);
			if(!file.exists() && !file.mkdirs()){
				Log.i(tag, "Create \""+spath+"\" fail!");
				return null;
			}
			if(!copyAssetsToFilesystem(dbfile, sfile)){
				Log.i(tag, String.format("Copy %s to %s fail!", dbfile, sfile));
				return null;
			}
			
			dbs.edit().putBoolean(dbfile, true).commit();
		}
		
		SQLiteDatabase db = SQLiteDatabase.openDatabase(sfile, null, SQLiteDatabase.NO_LOCALIZED_COLLATORS);
		if(db != null){
			databases.put(dbfile, db);
		}
		return db;
	}
	
	private String getDatabaseFilepath(){
		return String.format(databasepath, context.getApplicationInfo().packageName);
	}
	
	private String getDatabaseFile(String dbfile){
		return getDatabaseFilepath()+"/"+dbfile;
	}
	
	private boolean copyAssetsToFilesystem(String assetsSrc, String des){
		Log.i(tag, "Copy "+assetsSrc+" to "+des);
		InputStream istream = null;
		OutputStream ostream = null;
		try{
			AssetManager am = context.getAssets();
			istream = am.open(assetsSrc);
			ostream = new FileOutputStream(des);
			byte[] buffer = new byte[1024];
	    	int length;
	    	while ((length = istream.read(buffer))>0){
	    		ostream.write(buffer, 0, length);
	    	}
	    	istream.close();
	    	ostream.close();
		}
		catch(Exception e){
			e.printStackTrace();
			try{
				if(istream!=null)
			    	istream.close();
				if(ostream!=null)
			    	ostream.close();
			}
			catch(Exception ee){
				ee.printStackTrace();
			}
			return false;
		}
		return true;
	}
	
	/**
	 * Close assets database
	 * @param dbfile, the assets file which will be closed soon
	 * @return, the status of this operating
	 */
	public boolean closeDatabase(String dbfile){
		if(databases.get(dbfile) != null){
			SQLiteDatabase db = (SQLiteDatabase) databases.get(dbfile);
			db.close();
			databases.remove(dbfile);
			return true;
		}
		return false;
	}
	
	/**
	 * Close all assets database
	 */
	static public void closeAllDatabase(){
		Log.i(tag, "closeAllDatabase");
		if(mInstance != null){
			for(int i=0; i使用的過程也很簡單,應用程序開始的時候初始化一下,之後就可以在任意地方獲取管理器在通過assets文件夾下的數據庫文件名直接獲取SQLiteDatabase對象,之後對數據庫的操作就完全看你了。。。

簡單的使用例子:

// 初始化,只需要調用一次
AssetsDatabaseManager.initManager(getApplication());
// 獲取管理對象,因為數據庫需要通過管理對象才能夠獲取
AssetsDatabaseManager mg = AssetsDatabaseManager.getManager();
// 通過管理對象獲取數據庫
SQLiteDatabase db1 = mg.getDatabase("db1.db");
// 對數據庫進行操作
db1.execSQL("insert into tb([ID],[content]) values(null, 'db1');");
需要注意的是獲取數據庫對象的時候是區分數據庫文件名的大小寫的。


  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved