一、SQLite簡介
在Android平台上,集成了一個嵌入式關系型數據庫—SQLite,SQLite3支持 NULL、INTEGER、REAL(浮點數字)、TEXT(字符串文本)和BLOB(二進制對象)數據類型,雖然它支持的類型雖然只有五種,但實際上sqlite3也接受varchar(n)、char(n)、decimal(p,s) 等數據類型,只不過在運算或保存時會轉成對應的五種數據類型。 SQLite最大的特點是你可以保存任何類型的數據到任何字段中,無論這列聲明的數據類型是什么。例如:可以在Integer字段中存放字符串,或者在布爾型字段中存放浮點數,或者在字符型字段中存放日期型值。 但有一種情況例外:定義為INTEGER PRIMARY KEY的字段只能存儲64位整數, 當向這種字段中保存除整數以外的數據時,將會產生錯誤。另外, SQLite 在解析CREATE TABLE 語句時,會忽略 CREATE TABLE 語句中跟在字段名后面的數據類型信息。
二、SQLite的CURD
Android提供了一個名為SQLiteDatabase的類,該類封裝了一些操作數據庫的API,使用該類可以完成對數據進行添加(Create)、查詢(Retrieve)、更新(Update)和刪除(Delete)操作(這些操作簡稱為CRUD)。對SQLiteDatabase的學習,我們應該重點掌握execSQL()和rawQuery()方法。 execSQL()方法可以執行insert、delete、update和CREATE TABLE之類有更改行為的SQL語句;rawQuery()方法可以執行select語句。SQLiteDatabase還專門提供了對應於添加、刪除、更新、查詢的操作方法: insert()、delete()、update()和query() 。這些方法實際上是給那些不太了解SQL語法的菜鳥使用的,對於熟悉SQL語法的程序員而言,直接使用execSQL()和rawQuery()方法執行SQL語句就能完成數據的添加、刪除、更新、查詢操作。
三、SQLite的事務管理
使用SQLiteDatabase的beginTransaction()方法可以開啟一個事務,程序執行到endTransaction() 方法時會檢查事務的標志是否為成功,如果為成功則提交事務,否則回滾事務。當應用需要提交事務,必須在程序執行到endTransaction()方法之前使用setTransactionSuccessful() 方法設置事務的標志為成功,如果不調用setTransactionSuccessful() 方法,默認會回滾事務。
三、SQLite創建、更新數據表
如果應用使用到了SQLite數據庫,在用戶初次使用軟件時,需要創建應用使用到的數據庫表結構及添加一些初始化記錄,另外在軟件升級的時候,也需要對數據表結構進行更新。在Android系統,為我們提供了一個名為SQLiteOpenHelper的類,該類用於對數據庫版本進行管理,該類是一個抽象類,必須繼承它才能使用。為了實現對數據庫版本進行管理,SQLiteOpenHelper類有兩種重要的方法,分別是onCreate(SQLiteDatabase db)和onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion)
當調用SQLiteOpenHelper的getWritableDatabase()或者getReadableDatabase()方法獲取用於操作數據庫的SQLiteDatabase實例的時候,如果數據庫不存在,Android系統會自動生成一個數據庫,接着調用onCreate()方法,onCreate()方法在初次生成數據庫時才會被調用,在onCreate()方法里可以生成數據庫表結構及添加一些應用使用到的初始化數據。onUpgrade()方法在數據庫的版本發生變化時會被調用,數據庫的版本是由程序員控制的,假設數據庫現在的版本是1,由於業務的需要,修改了數據庫表的結構,這時候就需要升級軟件,升級軟件時希望更新用戶手機里的數據庫表結構,為了實現這一目的,可以把原來的數據庫版本設置為2(或其他數值),並且在onUpgrade()方法里面實現表結構的更新。當軟件的版本升級次數比較多,這時在onUpgrade()方法里面可以根據原版號和目標版本號進行判斷,然后作出相應的表結構及數據更新。
getWritableDatabase()和getReadableDatabase()方法都可以獲取一個用於操作數據庫的SQLiteDatabase實例。但getWritableDatabase() 方法以讀寫方式打開數據庫,一旦數據庫的磁盤空間滿了,數據庫就只能讀而不能寫,倘若使用的是getWritableDatabase() 方法就會出錯。getReadableDatabase()方法先以讀寫方式打開數據庫,如果數據庫的磁盤空間滿了,就會打開失敗,當打開失敗后會繼續嘗試以只讀方式打開數據庫。
在Android中可以使用Eclipse插件DDMS來查看,也可以使用Android工具包中的adb工具來查看。android項目中的sqlite數據庫位於/data/data/項目包/databases中。
DDMS中在File Explorer中找到上面所示目錄,可以直接導出對應的數據庫。
ADB查看數據塊:
1)運行cmd,切換到android-sdk目錄,運行adb.exe,加上參數shell,出現#號就代表進入了shell命令模式(adb shell),注意adb要在Android模擬器運行時才能進入shell.
2)shell命令記住兩個基本命令ls和cd,類似windows命令提示行中的dir和cd,代表列出當前目錄下文件列表和進入到指定目錄。了解這兩個命令之后,就可以找到data/data/項目包名/databases.
3) 找到數據庫文件,接下來就是使用sqlite管理工具來進行操作了。鍵入”sqlite3 數據庫名“就進入了qlite管理模式了。
說明:在android的sdk中自帶了sqlite3.exe,這是sqlite的官方管理工具,它是一個命令行工具。為了使用方便,將其路徑注冊到系統環境變量path中,即將;%Android_Home%加在Path中,這樣就能運行sqlite3,可以直接打開sqlite管理工具了。
4)sqlite管理數據庫
sqlite命令行工具默認是以;結束語句的。所以如果只是一行語句,要在末尾加;,或者在下一行中鍵入;,這樣sqlite命令才會被執行。
sqlite常用命令:
.tables--查看數據庫的表列表
.exit--退出sqlite命令行
其他命令可隨時.help查看幫助。sql命令可直接在此命令行上執行即可:
五、代碼案例
案例一:
public class SqliteHelper extends SQLiteOpenHelper {
private static final String DATABASE_NAME="xiangqiao_db";
private static final String TABLE_NAME="xiangqiao_table";
private static final int VERSION=1;
public SqliteHelper(Context context, String name, CursorFactory factory,
int version) {
super(context, name, factory, version);
}
public SqliteHelper(Context context) {
this(context, DATABASE_NAME, null, VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//創建數據表
String sql="create table "+TABLE_NAME+" (id integer primary key autoincrement,name varchar(20),content text,time date)";
sqLiteDatabase.execSQL(sql);
sqLiteDatabase.close();
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
// TODO Auto-generated method stub
}
}
public class DbDao {
SqliteHelper sqliteHelper;
public dbDao(Context context) {
this.sqliteHelper = new SqliteHelper(context);
}
public String exeQuery(String sql) {
SQLiteDatabase sqLiteDatabase = sqliteHelper.getReadableDatabase();
Cursor cursor = sqLiteDatabase.rawQuery(sql, null);
StringBuffer buffer = new StringBuffer();
while (cursor.moveToNext()) {
buffer.append(cursor.getInt(0)).append(" ")
.append(cursor.getString(1)).append(" ")
.append(cursor.getString(2)).append(" ")
.append(cursor.getString(3)).append(" ");
}
cursor.close();
sqLiteDatabase.close();
sqliteHelper.close();
return buffer.toString();
}
public void exeDO(String sql) {
SQLiteDatabase sqLiteDatabase = sqliteHelper.getWritableDatabase();
sqLiteDatabase.execSQL(sql);
sqLiteDatabase.close();
sqliteHelper.close();
}
}
public class MainActivity extends Activity {
public void DoDatabase(){
DbDao dbDao=new DbDao(getApplicationContext());
//增
dbDao.exeDO("insert into xiangqiao_table values(null,'xiangqiao','xiangqiao 的內容','2011-11-10 12:10:11')");
//改
dbDao.exeDO("update xiangqiao_table set name='123' where id=1");
//查
String result=dbDao.exeQuery("select * from xiangqiao_table order by id desc");
//刪
dbDao.exeDO("delete from xiangqiao_table where id=2");
}
案例二:

public class dbHelper extends SQLiteOpenHelper {
private final static String DATABASE_NAME="sec_db";
private final static int DATABASE_VERSION=1;
private final static String TABLE_NAME="sec_pwd";
public final static String FIELD_ID="_id";
public final static String FIELD_TITLE="sec_Title";
public dbHelper(Context context)
{
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase db) {
// TODO Auto-generated method stub
String sql="Create table "+TABLE_NAME+"("+FIELD_ID+" integer primary key autoincrement,"
+FIELD_TITLE+" text );";
db.execSQL(sql);
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
// TODO Auto-generated method stub
String sql=" DROP TABLE IF EXISTS "+TABLE_NAME;
db.execSQL(sql);
onCreate(db);
}
public Cursor select()
{
SQLiteDatabase db=this.getReadableDatabase();
Cursor cursor=db.query(TABLE_NAME, null, null, null, null, null, " _id desc");
return cursor;
}
public long insert(String Title)
{
SQLiteDatabase db=this.getWritableDatabase();
ContentValues cv=new ContentValues();
cv.put(FIELD_TITLE, Title);
long row=db.insert(TABLE_NAME, null, cv);
return row;
}
public void delete(int id)
{
SQLiteDatabase db=this.getWritableDatabase();
String where=FIELD_ID+"=?";
String[] whereValue={Integer.toString(id)};
db.delete(TABLE_NAME, where, whereValue);
}
public void update(int id,String Title)
{
SQLiteDatabase db=this.getWritableDatabase();
String where=FIELD_ID+"=?";
String[] whereValue={Integer.toString(id)};
ContentValues cv=new ContentValues();
cv.put(FIELD_TITLE, Title);
db.update(TABLE_NAME, cv, where, whereValue);
}
}
--------------------------------------------------------------------
PS: 歡迎關注公眾號"Devin說",會不定期更新Java相關技術知識。
--------------------------------------------------------------------