Android本地數據存儲之SQLite關係型數據庫 ——SQLiteDatabase

原文:http://blog.csdn.net/omg_2012/article/details/8041186


數據庫的創建,獲取,執行sql語句:

框架搭建:dao


思考:

1.數據庫保存在哪裏?

2.如何創建數據庫?如何創建表?

3.如何更新數據庫?如何更改表的列數據?

4.如何獲取數據庫?

5.如何修改數據庫中的表的數據?


框架思想

思考:如何使得編程更加簡單?

一個sql語言,容易寫錯;

1.使用佔位符;

2.框架解析重建法:搭建框架,對增刪改查功能進行單獨封裝,傳入容器對象即可;



思考:

1.數據庫保存在哪裏?

data/data/包名/databases/xiaoo.db

2.如何創建數據庫?如何創建表?

db.execSQL("CREATE TABLE person (personid integer primary key autoincrement, name varchar(20))");

3.如何更新數據庫?如何更改表的列數據?

db.execSQL("ALTER TABLE person ADD phone VARCHAR(12) NULL ");

4.如何獲取數據庫?

5.如何修改數據庫中的表的數據?



一、創建數據庫打開助手:

二、創建dao

三、測試dao

[plain] view plaincopy
  1. import android.content.Context;  
  2. import android.database.sqlite.SQLiteDatabase;  
  3. import android.database.sqlite.SQLiteOpenHelper;  
  4.   
  5. public class MyDBOpenHelper extends SQLiteOpenHelper {  
  6.   
  7.     /**  
  8.      *   
  9.      * @param context 應用程序上下文  
  10.      * @param name    數據庫的名字  
  11.      * @param factory 查詢數據庫的遊標工廠 一般情況下 用sdk默認的  
  12.      * @param version  數據庫的版本 版本號必須不小1   
  13.      *    
  14.      */  
  15.     public MyDBOpenHelper(Context context) {  
  16.         super(context, "xiaoo.db", null, 6);  
  17.     }  
  18.   
  19.     // 在mydbOpenHelper 在數據庫第一次被創建的時候  會執行onCreate();  
  20.     @Override  
  21.     public void onCreate(SQLiteDatabase db) {  
  22.         System.out.println("我被調用了 oncreate");  
  23.         db.execSQL("CREATE TABLE person (personid integer primary key autoincrement, name varchar(20))");  
  24.     }  
  25.         // 通過version的增加來執行數據庫版本更新,版本號改爲6的同時,調用onUpgrade ,讓程序員執行具體更新;  
  26.     @Override  
  27.     public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {  
  28.         System.out.println("on update ");  
  29.         db.execSQL("ALTER TABLE person ADD phone VARCHAR(12) NULL ");  
  30.     }  
  31. }  

二、創建dao

[html] view plaincopy
  1. import java.util.ArrayList;  
  2. import java.util.List;  
  3.   
  4. import android.content.Context;  
  5. import android.database.Cursor;  
  6. import android.database.sqlite.SQLiteDatabase;  
  7. import android.util.Log;  
  8. import cn.itcast.db.MyDBOpenHelper;  
  9. import cn.itcast.db.domain.Person;  
  10.   
  11. public class PersonDao {  
  12.     private static final String TAG = "PersonDao";  
  13.     private MyDBOpenHelper dbOpenHelper;  
  14.   
  15.     // 在personDao被new出來的時候 就完成初始化  
  16.   
  17.     public PersonDao(Context context) {  
  18.         dbOpenHelper = new MyDBOpenHelper(context);  
  19.         // dbOpenHelper.getReadableDatabase()  
  20.         // dbOpenHelper.getWritableDatabase()  
  21.     }  
  22.   
  23.     // 增刪改查  
  24.   
  25.     /**  
  26.      * 往數據庫添加一條數據  
  27.      */  
  28.     public void add(String name, String phone) {  
  29.         boolean result = find(name);  
  30.         if (result)  
  31.             return;  
  32.   
  33.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  34.         if (db.isOpen()) {  
  35.             db.execSQL("insert into person (name,phone) values (?,?)",  
  36.                     new Object[] { name, phone });  
  37.             // 關閉數據庫 釋放數據庫的鏈接  
  38.             db.close();  
  39.         }  
  40.     }  
  41.   
  42.     /**  
  43.      * 查找數據庫的操作  
  44.      */  
  45.     public boolean find(String name) {  
  46.         boolean result = false;  
  47.         SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
  48.         if (db.isOpen()) {  
  49.             Cursor cursor = db.rawQuery("select * from person where name=?",  
  50.                     new String[] { name });  
  51.             if (cursor.moveToFirst()) {  
  52.                 int index = cursor.getColumnIndex("phone"); // 得到phone在表中是第幾列  
  53.                 String phone = cursor.getString(index);  
  54.                 Log.i(TAG, "phone =" + phone);  
  55.                 result = true;  
  56.   
  57.             }  
  58.             // 記得關閉掉 cursor  
  59.             cursor.close();  
  60.             result = false;  
  61.             // 釋放數據庫的鏈接  
  62.             db.close();  
  63.         }  
  64.         return result;  
  65.     }  
  66.   
  67.     /**  
  68.      * 刪除一條記錄  
  69.      *   
  70.      * @param name  
  71.      */  
  72.     public void delete(String name) {  
  73.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  74.         if (db.isOpen()) {  
  75.             db.execSQL("delete from person where name =?",  
  76.                     new Object[] { name });  
  77.             db.close();  
  78.         }  
  79.     }  
  80.   
  81.     /**  
  82.      * 更新一條記錄  
  83.      *   
  84.      */  
  85.     public void update(String name, String newname, String newphone) {  
  86.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  87.         if (db.isOpen()) {  
  88.             db.execSQL("update person set name=? , phone=? where name=?",  
  89.                     new Object[] { newname, newphone, name });  
  90.             db.close();  
  91.         }  
  92.     }  
  93.   
  94.     /**  
  95.      * 查找全部  
  96.      */  
  97.     public List<Person> getAllPersons() {  
  98.         List<Person> persons=null;  
  99.         SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
  100.         if (db.isOpen()) {  
  101.             persons = new ArrayList<Person>();  
  102.             Cursor cursor = db.rawQuery("select * from person ", null);  
  103.             while (cursor.moveToNext()) {  
  104.                 Person person = new Person();  
  105.                 int nameindex = cursor.getColumnIndex("name");  
  106.                 int phoneindex = cursor.getColumnIndex("phone");  
  107.                 String name = cursor.getString(nameindex);  
  108.                 String phone = cursor.getString(phoneindex);  
  109.                 person.setName(name);  
  110.                 person.setNumber(phone);  
  111.                 persons.add(person);  
  112.             }  
  113.             cursor.close();  
  114.             db.close();  
  115.         }  
  116.         return persons;  
  117.     }  
  118.   
  119. }  


三、單元測試:測試dao

1.配置

[html] view plaincopy
  1. instrumentation 和 uses-library  

[html] view plaincopy
  1. <instrumentation  
  2.     android:name="android.test.InstrumentationTestRunner"   //使用測試框架中的哪個測試運行器  
  3.     android:targetPackage="cn.xiaoo.db" />      //測試哪個工程?  
  4.   
  5. <application  
  6.     android:icon="@drawable/ic_launcher"  
  7.     android:label="@string/app_name" >  
  8.     <uses-library android:name="android.test.runner" />      //該程序需要添加哪個jar包(用於測試)?  


2.編程測試

[plain] view plaincopy
  1. package cn.itcast.db.dao.test;  
  2.   
  3. import java.util.List;  
  4.   
  5. import cn.itcast.db.dao.PersonDao;  
  6. import cn.itcast.db.domain.Person;  
  7. import android.test.AndroidTestCase;  
  8.   
  9. public class TestPersonDao extends AndroidTestCase {  
  10.     PersonDao dao;  
  11.     // 測試在執行測試代碼時候的流程   
  12.     //1 .new TestPersonDao 框架new出來   
  13.     //2. 調用 setUp()  
  14.     //3. testAdd()  這個時候 上下文 才被創建出來   
  15.       
  16.       
  17. /*  @Override  
  18.     protected void setUp() throws Exception {  
  19.         dao = new PersonDao(getContext());  
  20.         super.setUp();  
  21.     }*/  
  22.     public void testAdd() throws Exception{  
  23.         PersonDao dao = new PersonDao(getContext());  
  24.         for(int i=0;i<100;i++){  
  25.         dao.add("lisi"+i, "123456789"+i);  
  26.         }  
  27.     }  
  28.     public void testdelete() throws Exception{  
  29.         PersonDao dao = new PersonDao(getContext());  
  30.         dao.delete("lisi99");  
  31.     }  
  32.     public void testupdate() throws Exception{  
  33.         PersonDao dao = new PersonDao(getContext());  
  34.         dao.update("lisi98", "wangwu", "120");  
  35.     }  
  36.       
  37.     public void testFindAll() throws Exception{  
  38.         PersonDao dao = new PersonDao(getContext());  
  39.         List<Person>  persons  = dao.getAllPersons();  
  40.         assertEquals("testFindAll獲取集合的大小",98, persons.size());  
  41.     }  
  42.       
  43.     /**  
  44.      * 測試的流程:  
  45.      */  
  46.     /*  
  47.     [2012-10-05 13:47:51 - db] ------------------------------  
  48.     [2012-10-05 13:47:51 - db] Android Launch!    //系統啓動  
  49.     [2012-10-05 13:47:51 - db] adb is running normally.   //調試橋正常運行  
  50.     [2012-10-05 13:47:51 - db] Performing android.test.InstrumentationTestRunner JUnit launch   //運行測試運行器,啓動JUnit  
  51.     [2012-10-05 13:47:51 - db] Automatic Target Mode: using existing emulator 'emulator-5554' running compatible AVD '2.3.3_QVGA'  
  52.     [2012-10-05 13:47:53 - db] Application already deployed. No need to reinstall.//不需要重新安裝  
  53.     [2012-10-05 13:47:53 - db] Launching instrumentation android.test.InstrumentationTestRunner on device emulator-5554//在設備上運行測試運行器  
  54.     [2012-10-05 13:47:53 - db] Collecting test information //收集運行信息  
  55.     [2012-10-05 13:47:56 - db] Sending test information to Eclipse  //發送測試信息到Eclipse  
  56.     [2012-10-05 13:47:56 - db] Running tests...    //執行代碼  
  57.     [2012-10-05 13:47:58 - db] Test run finished   //執行完畢  
  58.     */  
  59.  }  


框架思想

思考:如何使得編程更加簡單?

一條sql語句,容易寫錯;

[html] view plaincopy
  1. 操作表  
  2. insert into person (name,phone) values (?,?)---------public long insert(String table, String nullColumnHack, ContentValues values)  
  3. delete from person where name =?---------------------public int delete(String table, String whereClause, String[] whereArgs)  
  4. update person set name=? , phone=? where name=?------public int update(String table, ContentValues values, String whereClause, String[] whereArgs)  
  5. select * from person where name=?--------------------public Cursor query(boolean distinct, String table, String[] columns,  
  6.                                                                          String selection, String[] selectionArgs, String groupBy,  
  7.                                                                          String having, String orderBy, String limit)  
  8. insert:在哪張表插入哪些數據?string string contentvalues  
  9. delete:在哪張表刪除哪些數據?String String String[]  
  10. update:在哪張表的那條數據上更改什麼數據? String ContentValues String  String[]  
  11. query:是否保證唯一?查哪張表?查哪些列?  
  12.        什麼查詢條件?佔位符值?分組?  
  13.        包含?排序?區間?  
  14. 操作數據庫:  
  15. CREATE TABLE person (personid integer primary key autoincrement, name varchar(20))  
  16. ALTER TABLE person ADD phone VARCHAR(12) NULL   

怎辦辦?

1.使用佔位符;

2.框架解析重建法:搭建框架,對增刪改查功能進行單獨封裝,傳入容器對象即可;

[java] view plaincopy
  1. 1.原生:  db.execSQL("insert into person (name,age) values ("xiaoli",20)");  
  2.   
  3. 2.站位符:db.execSQL("insert into person (name,age) values (?,?)",new Object[]{"xiaoli",20});  
  4.   
  5. 3.框架 :  
  6.   
  7.             ContentValues values = new ContentValues();  
  8.             values.put("name", name);  
  9.             values.put("age", age);  
  10.             db.insert("person"null, values);  
  11.   
  12.  public void add(String name, int age) {  
  13.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  14.         if (db.isOpen()) {  
  15.              
  16.             ContentValues values = new ContentValues();  
  17.             values.put("name", name);  
  18.             values.put("age", age);  
  19.             // 如果 contentvalues爲空  
  20.             db.insert("person"null, values); // 組拼sql語句完成的添加的操作  
  21.               
  22.             // insert into person name values (NULL) ;  
  23.             db.close();  
  24.         }  
  25. }  

最複雜的方法是查詢:query

我們一起來看看底層是怎麼封裝的:

[java] view plaincopy
  1. public static String buildQueryString(  
  2.         boolean distinct, String tables, String[] columns, String where,  
  3.         String groupBy, String having, String orderBy, String limit) {  
  4.     if (TextUtils.isEmpty(groupBy) && !TextUtils.isEmpty(having)) {  
  5.         throw new IllegalArgumentException(  
  6.                 "HAVING clauses are only permitted when using a groupBy clause");  
  7.     }  
  8.     if (!TextUtils.isEmpty(limit) && !sLimitPattern.matcher(limit).matches()) {  
  9.         throw new IllegalArgumentException("invalid LIMIT clauses:" + limit);  
  10.     }  
  11.   
  12.     StringBuilder query = new StringBuilder(120);  
  13.   
  14.     query.append("SELECT ");  
  15.     if (distinct) {  
  16.         query.append("DISTINCT ");  
  17.     }  
  18.     if (columns != null && columns.length != 0) {  
  19.         appendColumns(query, columns);  
  20.     } else {  
  21.         query.append("* ");  
  22.     }  
  23.     query.append("FROM ");  
  24.     query.append(tables);  
  25.     appendClause(query, " WHERE ", where);  
  26.     appendClause(query, " GROUP BY ", groupBy);  
  27.     appendClause(query, " HAVING ", having);  
  28.     appendClause(query, " ORDER BY ", orderBy);  
  29.     appendClause(query, " LIMIT ", limit);  
  30.   
  31.     return query.toString();  
  32. }  


另一種增刪改查:dao


[html] view plaincopy
  1. import java.util.ArrayList;  
  2. import java.util.List;  
  3.   
  4. import cn.itcast.db.MyDBOpenHelper;  
  5. import cn.itcast.db.domain.Person;  
  6. import android.content.ContentValues;  
  7. import android.content.Context;  
  8. import android.database.Cursor;  
  9. import android.database.sqlite.SQLiteDatabase;  
  10.   
  11. public class PersonDBDao {  
  12.     private Context context;  
  13.     MyDBOpenHelper dbOpenHelper;  
  14.   
  15.     public PersonDBDao(Context context) {  
  16.         this.context = context;  
  17.         dbOpenHelper = new MyDBOpenHelper(context);  
  18.     }  
  19.   
  20.     /**  
  21.      * 添加一條記錄  
  22.      */  
  23.     public void add(String name, int age) {  
  24.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  25.         if (db.isOpen()) {  
  26.             // db.execSQL("insert into person (name,age) values (?,?)",new  
  27.             // Object[]{name,age});  
  28.             // db.execSQL("insert into person ",null) // 不合法的sql語句  
  29.             ContentValues values = new ContentValues();  
  30.             values.put("name", name);  
  31.             values.put("age", age);  
  32.             // 如果 contentvalues爲空  
  33.             db.insert("person", null, values); // 組拼sql語句完成的添加的操作  
  34.               
  35.             // insert into person name values (NULL) ;  
  36.             db.close();  
  37.         }  
  38.   
  39.     }  
  40.   
  41.     /**  
  42.      * 刪除一條記錄  
  43.      */  
  44.     public void delete(String name) {  
  45.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  46.         if (db.isOpen()) {  
  47.             db.delete("person", "name=?", new String[] { name });  
  48.             db.close();  
  49.         }  
  50.     }  
  51.   
  52.     /**  
  53.      * 數據庫的更改操作  
  54.      */  
  55.     public void update(String name, String newname, int newage) {  
  56.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  57.         if (db.isOpen()) {  
  58.             ContentValues values = new ContentValues();  
  59.             values.put("name", newname);  
  60.             values.put("age", newage);  
  61.             db.update("person", values, "name=?", new String[] { name });  
  62.             db.close();  
  63.         }  
  64.     }  
  65.   
  66.     /**  
  67.      * 數據庫的查詢操作  
  68.      */  
  69.     public boolean find(String name) {  
  70.         boolean result = false;  
  71.         SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
  72.         if (db.isOpen()) {  
  73.             // select * from person  
  74.             Cursor cursor = db.query("person", null, "name=?",  
  75.                     new String[] { name }, null, null, null);  
  76.             if (cursor.moveToFirst()) {  
  77.                 result = true;  
  78.             }  
  79.             cursor.close();  
  80.             db.close();  
  81.         }  
  82.         return result;  
  83.   
  84.     }  
  85.   
  86.     /**  
  87.      * 查詢所有信息  
  88.      */  
  89.     public List<Person> findAll() {  
  90.         List<Person> persons = null;  
  91.         SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
  92.         if (db.isOpen()) {  
  93.             Cursor cursor = db.query("person", null, null, null, null, null,  
  94.                     null);  
  95.             persons = new ArrayList<Person>();  
  96.             while (cursor.moveToNext()) {  
  97.                 Person person = new Person();  
  98.                 String name = cursor.getString(cursor.getColumnIndex("name"));  
  99.                 person.setName(name);  
  100.                 int age = cursor.getInt(cursor.getColumnIndex("age"));  
  101.                 person.setAge(age);  
  102.                 persons.add(person);  
  103.             }  
  104.             cursor.close();  
  105.             db.close();  
  106.         }  
  107.         return persons;  
  108.     }  
  109.     /**  
  110.      * 查詢所有信息  
  111.      */  
  112.     public Cursor findAllbyCursor() {  
  113.         SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
  114.         if (db.isOpen()) {  
  115.             /*Cursor cursor = db.query("person", null, null, null, null, null,  
  116.                     null);*/  
  117.             Cursor cursor = db.rawQuery("select personid as _id,age,name from person", null);  
  118.               
  119.             return cursor;  
  120.             // 注意了  一定不要把數據庫 關閉了   
  121.             }  
  122.         return null;  
  123.           
  124.     }  
  125.   
  126.        /**  
  127.         * 銀行轉賬的方法  
  128.         * 1.開始事務:db.beginTransaction();  
  129.         * 2.設置事務成功:db.setTransactionSuccessful();  
  130.         * 3.結束事務:db.endTransaction();  
  131.         * 4.關閉連接:db.close();  
  132.         */  
  133.     public void transaction() {  
  134.         SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
  135.         if (db.isOpen()) {  
  136.   
  137.             try {  
  138.                 // 開啓數據庫的事務  
  139.                 db.beginTransaction();  
  140.                 // 給張三設置1000塊錢的賬戶  
  141.                 db.execSQL("update person set account=? where name=?",  
  142.                         new Object[] { 1000, "zhangsan98" });  
  143.                 // 把張三的賬戶扣除200塊錢  
  144.                 db.execSQL("update person set account=account-? where name=?",  
  145.                         new Object[] { 200, "zhangsan98" });  
  146.                 // 出現了異常  
  147.                 // 把張三的錢給李四  
  148.                 //初始化李四賬戶 爲 0  
  149.                 db.execSQL("update person set account=? where name=?",  
  150.                         new Object[] { 0, "lisi" });  
  151.                 db.execSQL("update person set account=account+? where name=?",  
  152.                         new Object[] { 200, "lisi" });  
  153.                 db.setTransactionSuccessful();  
  154.             }  
  155.             // 顯示的設置事務是否成功  
  156.             catch (Exception e) {  
  157.                 // TODO: handle exception  
  158.             } finally {  
  159.                 db.endTransaction();  
  160.                 db.close();  
  161.             }  
  162.         }  
  163.     }  
  164. }  

發佈了12 篇原創文章 · 獲贊 21 · 訪問量 18萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章