數據庫SQLite介紹
Android使用getWritableDatabase()和getReadableDatabase()方法都可以獲取一個用於操作數據庫的SQLiteDatabase實例。
getReadableDatabase()方法中會調用getWritableDatabase()方法
其中
getWritableDatabase() 方法以讀寫方式打開數據庫,一旦數據庫的磁盤空間滿了,數據庫就只能讀而不能寫,倘若使用的是getWritableDatabase() 方法就會出錯。
getReadableDatabase()方法則是先以讀寫方式打開數據庫,如果數據庫的磁盤空間滿了,就會打開失敗,當打開失敗后會繼續嘗試以只讀方式打開數據庫。如果該問題成功解決,則只讀數據庫對象就會關閉,然后返回一個可讀寫的數據庫對象。
- 它會調用並返回一個可以讀寫數據庫的對象
 - 在第一次調用時會調用onCreate的方法
 - 當數據庫存在時會調用onOpen方法
 - 結束時調用onClose方法
 
4. 區別
是不是上面兩個總結一樣?
 然后事實呢?
- 兩個方法都是返回讀寫數據庫的對象,但是當磁盤已經滿了時,
getWritableDatabase會拋異常,而getReadableDatabase不會報錯,它此時不會返回讀寫數據庫的對象,而是僅僅返回一個讀數據庫的對象。 -  
getReadableDatabase會在問題修復后繼續返回一個讀寫的數據庫對象。 - 兩者都是數據庫操作,可能存在延遲等待,所以盡量不要在主線程中調用。
 
創建與刪除數據庫
封裝一個類去繼承SQLiteOpenHelper 在構造函數中傳入數據庫名稱與數據庫版本號,
封裝了一個DatabaseHelper類繼承SQLiteOpenHelper 我使用了設計模式中的單例模式來處理這個類,這里說一下單例模式 單例模式是常見的代碼設計模式之一 它的好處是在於避免在內存中頻繁的實例化所以將它的對象寫成static 靜態 這樣它的對象就只有一份存在靜態內存區使用的時候只須要通過getInstance()就可以直接拿到這個靜態對象。
1 public class DatabaseHelper extends SQLiteOpenHelper { 2 private static DatabaseHelper mInstance = null; 3 4 /** 數據庫名稱 **/ 5 public static final String DATABASE_NAME = "xys.db"; 6 7 /** 數據庫版本號 **/ 8 private static final int DATABASE_VERSION = 1; 9 10 /**數據庫SQL語句 添加一個表**/ 11 private static final String NAME_TABLE_CREATE = "create table test(" 12 + "_id INTEGER PRIMARY KEY AUTOINCREMENT," + "name TEXT,"+"hp INTEGER DEFAULT 100,"+ "mp INTEGER DEFAULT 100," 13 + "number INTEGER);"; 14 15 DatabaseHelper(Context context) { 16 super(context, DATABASE_NAME, null, DATABASE_VERSION); 17 } 18 19 /**單例模式**/ 20 static synchronized DatabaseHelper getInstance(Context context) { 21 if (mInstance == null) { 22 mInstance = new DatabaseHelper(context); 23 } 24 return mInstance; 25 } 26 27 @Override 28 public void onCreate(SQLiteDatabase db) { 29 /**向數據中添加表**/ 30 db.execSQL(NAME_TABLE_CREATE); 31 } 32 33 @Override 34 public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { 35 /**可以拿到當前數據庫的版本信息 與之前數據庫的版本信息 用來更新數據庫**/ 36 } 37 38 39 /** 40 * 刪除數據庫 41 * @param context 42 * @return 43 */ 44 public boolean deleteDatabase(Context context) { 45 return context.deleteDatabase(DATABASE_NAME); 46 } 47 }
在這個類中使用DatabaseHelper對象 實現創建與刪除數據庫、
1 public class NewSQLite extends Activity { 2 DatabaseHelper mDbHelper = null; 3 SQLiteDatabase mDb = null; 4 Context mContext = null; 5 @Override 6 protected void onCreate(Bundle savedInstanceState) { 7 setContentView(R.layout.create_sql); 8 mContext = this; 9 //創建DatabaseHelper對象 10 mDbHelper = DatabaseHelper.getInstance(mContext); 11 //調用getReadableDatabase方法如果數據庫不存在 則創建 如果存在則打開 12 mDb= mDbHelper.getReadableDatabase(); 13 14 Button button0 = (Button)findViewById(R.id.createDateBase); 15 button0.setOnClickListener(new OnClickListener() { 16 17 @Override 18 public void onClick(View arg0) { 19 20 Toast.makeText(NewSQLite.this, "成功創建數據庫", Toast.LENGTH_LONG).show(); 21 } 22 }); 23 Button button1 = (Button)findViewById(R.id.deleteDateBase); 24 button1.setOnClickListener(new OnClickListener() { 25 26 @Override 27 public void onClick(View arg0) { 28 mDbHelper = DatabaseHelper.getInstance(mContext); 29 // 調用getReadableDatabase方法如果數據庫不存在 則創建 如果存在則打開 30 mDb = mDbHelper.getReadableDatabase(); 31 // 關閉數據庫 32 mDbHelper.close(); 33 // 刪除數據庫 34 mDbHelper.deleteDatabase(mContext); 35 Toast.makeText(NewSQLite.this, "成功刪除數據庫", Toast.LENGTH_LONG).show(); 36 } 37 }); 38 39 40 41 super.onCreate(savedInstanceState); 42 } 43 44 }
創建的數據庫會被保存在當前項目中 databases 路徑下
數據庫是可以由多張數據表組成的 如果添加一張數據庫的表的話 可以使用 數據庫語句 create table 名稱(內容) 來進行添加 。這里給出一條創建數據庫的語句 。 意思是創建一張表 名稱為gameInfo 表中包含的字段 為 _id 為INTEGER 類型 並且遞增 name 為Text類型 hp mp 為INTEGER 默認數值為100 number 為INTEGER 類型。
使用SQLiteDatabase對象調用 insert()方法 傳入標的名稱與ContentValues 添加的內容 則可以向數據庫表中寫入一條數據 delete ()為刪除一條數據 update()為更新一條數據。
我詳細說一下查找一條數據使用的方法 query 中 跟了8個參數
public Cursor query(String table,String[] columns,String selection,String[] selectionArgs,String groupBy,String having,String orderBy,String limit);
參數說明:
table:數據庫表的名稱
columns:數據庫列名稱數組 寫入后最后返回的Cursor中只能查到這里的列的內容
selection:查詢條件
selectionArgs:查詢結果
groupBy:分組列
having:分組條件
orderBy:排序列
limit:分頁查詢限制
Cursor:返回值,將查詢到的結果都存在Cursor
Cursor是一個游標接口,每次查詢的結果都會保存在Cursor中 可以通過遍歷Cursor的方法拿到當前查詢到的所有信息。
Cursor的方法
moveToFirst() //將Curor的游標移動到第一條moveToLast()///將Curor的游標移動到最后一條
move(int offset)//將Curor的游標移動到指定ID
moveToNext()//將Curor的游標移動到下一條
moveToPrevious()//將Curor的游標移動到上一條
getCount() //得到Cursor 總記錄條數
isFirst() //判斷當前游標是否為第一條記錄
isLast()//判斷當前游標是否為最后一條數據
getInt(int columnIndex) //根據列名稱獲得列索引ID
getString(int columnIndex)//根據索引ID 拿到表中存的字段
1 private void query(SQLiteDatabase db) { 2 // 把整張表的所有數據query到cursor中 3 Cursor cursor = db.query(TABLE_NAME, null, null, null, null, null, null); 4 //判斷cursor不為空 這個很重要 5 if (cursor != null) { 6 // 循環遍歷cursor 7 while (cursor.moveToNext()) { 8 // 拿到每一行name 與hp的數值 9 String name = cursor.getString(cursor.getColumnIndex("name")); 10 String hp = cursor.getString(cursor.getColumnIndex("hp")); 11 Log.v("info", "姓名是 " + name + "hp為 " + hp); 12 } 13 // 關閉 14 cursor.close(); 15 } 16 }
