SQLite开发实例

上一篇文章介绍了SQLite的一些基本用法,本篇文章是一个SQLite在项目中的实际例子。

实际开发中,为了能够更好的管理和维护数据库,我们会封装一个继承自SQLiteOpenHelper类的数据库操作类,然后以这个类为基础,再封装我们的业务逻辑方法。


目录结构



DBHelper继承了SQLiteOpenHelper,作为维护和管理数据库的基类,DBManager是建立在DBHelper之上,封装了常用的业务方法,Person是我们的person表对应的JavaBean.


DBHelper

package com.example.daniel.test.db;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

/**
 * Created by Daniel on 10/12/2015.
 */
public class DBHelper extends SQLiteOpenHelper {

    private static final String DATABASE_NAME = "test.db";
    private static final int DATABASE_VERSION = 1;

    public DBHelper(Context context) {
        //CursorFactory设置为null,使用默认值
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
    }

    //数据库第一次被创建时onCreate会被调用
    @Override
    public void onCreate(SQLiteDatabase db) {
        db.execSQL("CREATE TABLE IF NOT EXISTS person" +
                "(_id INTEGER PRIMARY KEY AUTOINCREMENT, name VARCHAR, age INTEGER, info TEXT)");
    }

    //如果DATABASE_VERSION值被改为2,系统发现现有数据库版本不同,即会调用onUpgrade
    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {

    }
}


DBManager

package com.example.daniel.test.db;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;

import java.util.ArrayList;
import java.util.List;

/**
 * Created by Daniel on 10/12/2015.
 */
public class DBManager {
    private DBHelper helper;
    private SQLiteDatabase db;

    public DBManager(Context context) {
        helper = new DBHelper(context);
        //因为getWritableDatabase内部调用了mContext.openOrCreateDatabase(mName, 0, mFactory);
        //所以要确保context已初始化,我们可以把实例化DBManager的步骤放在Activity的onCreate里
        db = helper.getWritableDatabase();
    }

    /**
     * add persons
     *
     * @param persons
     */
    public void add(List<Person> persons) {
        db.beginTransaction();  //开始事务
        try {
            for (Person person : persons) {
                db.execSQL("INSERT INTO person VALUES(null, ?, ?, ?)", new Object[]{person.name, person.age, person.info});
            }
            db.setTransactionSuccessful();  //设置事务成功完成
        } finally {
            db.endTransaction();    //结束事务
        }
    }

    /**
     * update person's age
     *
     * @param person
     */
    public void updateAge(Person person) {
        ContentValues cv = new ContentValues();
        cv.put("age", person.age);
        db.update("person", cv, "name = ?", new String[]{person.name});
    }

    /**
     * delete old person
     *
     * @param person
     */
    public void deleteOldPerson(Person person) {
        db.delete("person", "age >= ?", new String[]{String.valueOf(person.age)});
    }

    /**
     * query all persons, return list
     *
     * @return List<Person>
     */
    public List<Person> query() {
        ArrayList<Person> persons = new ArrayList<Person>();
        Cursor c = queryTheCursor();
        while (c.moveToNext()) {
            Person person = new Person();
            person._id = c.getInt(c.getColumnIndex("_id"));
            person.name = c.getString(c.getColumnIndex("name"));
            person.age = c.getInt(c.getColumnIndex("age"));
            person.info = c.getString(c.getColumnIndex("info"));
            persons.add(person);
        }
        c.close();
        return persons;
    }

    /**
     * query all persons, return cursor
     *
     * @return Cursor
     */
    public Cursor queryTheCursor() {
        Cursor c = db.rawQuery("SELECT * FROM person", null);
        return c;
    }

    /**
     * close database
     */
    public void closeDB() {
        db.close();
    }
}


Person

package com.example.daniel.test.db;

/**
 * Created by Daniel on 10/12/2015.
 */
public class Person {
    public int _id;
    public String name;
    public int age;
    public String info;

    public Person() {
    }

    public Person(String name, int age, String info) {
        this.name = name;
        this.age = age;
        this.info = info;
    }
}

MainActivity

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import android.app.Activity;
import android.database.Cursor;
import android.database.CursorWrapper;
import android.os.Bundle;
import android.view.View;
import android.widget.ListView;
import android.widget.SimpleAdapter;
import android.widget.SimpleCursorAdapter;


public class MainActivity extends Activity {
   
	private DBManager mgr;
	private ListView listView;
	
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        listView = (ListView) findViewById(R.id.listView);
        //初始化DBManager
        mgr = new DBManager(this);
    }
    
    @Override
    protected void onDestroy() {
    	super.onDestroy();
    	//应用的最后一个Activity关闭时应释放DB
    	mgr.closeDB();
    }
    
    public void add(View view) {
    	ArrayList<Person> persons = new ArrayList<Person>();
    	
    	Person person1 = new Person("Ella", 22, "lively girl");
    	Person person2 = new Person("Jenny", 22, "beautiful girl");
    	Person person3 = new Person("Jessica", 23, "sexy girl");
    
    	persons.add(person1);
    	persons.add(person2);
    	persons.add(person3);
    
    	
    	mgr.add(persons);
    }
    
    public void update(View view) {
    	Person person = new Person();
    	person.name = "Jane";
    	person.age = 30;
    	mgr.updateAge(person);
    }
    
    public void delete(View view) {
    	Person person = new Person();
    	person.age = 30;
    	mgr.deleteOldPerson(person);
    }
    
    public void query(View view) {
    	List<Person> persons = mgr.query();
    	ArrayList<Map<String, String>> list = new ArrayList<Map<String, String>>();
    	for (Person person : persons) {
    		HashMap<String, String> map = new HashMap<String, String>();
    		map.put("name", person.name);
    		map.put("info", person.age + " years old, " + person.info);
    		list.add(map);
    	}
    	SimpleAdapter adapter = new SimpleAdapter(this, list, android.R.layout.simple_list_item_2,
    				new String[]{"name", "info"}, new int[]{android.R.id.text1, android.R.id.text2});
    	listView.setAdapter(adapter);
    }
    
    public void queryTheCursor(View view) {
    	Cursor c = mgr.queryTheCursor();
    	startManagingCursor(c);	//托付给activity根据自己的生命周期去管理Cursor的生命周期
    	CursorWrapper cursorWrapper = new CursorWrapper(c) {
    		@Override
    		public String getString(int columnIndex) {
    			//将简介前加上年龄
    			if (getColumnName(columnIndex).equals("info")) {
    				int age = getInt(getColumnIndex("age"));
    				return age + " years old, " + super.getString(columnIndex);
    			}
    			return super.getString(columnIndex);
    		}
    	};
    	//确保查询结果中有"_id"列
		SimpleCursorAdapter adapter = new SimpleCursorAdapter(this, android.R.layout.simple_list_item_2, 
				cursorWrapper, new String[]{"name", "info"}, new int[]{android.R.id.text1, android.R.id.text2});
		ListView listView = (ListView) findViewById(R.id.listView);
		listView.setAdapter(adapter);
    }
}

注意的SimpleCursorAdapter的应用,当我们使用这个适配器时,我们必须先得到一个Cursor对象,这里面有几个问题:如何管理Cursor的生命周期,如果包装Cursor,Cursor结果集都需要注意什么。
如果手动去管理Cursor的话会非常的麻烦,还有一定的风险,处理不当的话运行期间就会出现异常,幸好Activity为我们提供了startManagingCursor(Cursor cursor)方法,它会根据Activity的生命周期去管理当前的Cursor对象
/**
     * This method allows the activity to take care of managing the given
     * {@link Cursor}'s lifecycle for you based on the activity's lifecycle.
     * That is, when the activity is stopped it will automatically call
     * {@link Cursor#deactivate} on the given Cursor, and when it is later restarted
     * it will call {@link Cursor#requery} for you.  When the activity is
     * destroyed, all managed Cursors will be closed automatically.
     * 
     * @param c The Cursor to be managed.
     * 
     * @see #managedQuery(android.net.Uri , String[], String, String[], String)
     * @see #stopManagingCursor
     */
startManagingCursor方法会根据Activity的生命周期去管理当前的Cursor对象的生命周期,就是说当Activity停止时他会自动调用Cursor的deactivate方法,禁用游标,当Activity重新回到屏幕时它会调用Cursor的requery方法再次查询,当Activity摧毁时,被管理的Cursor都会自动关闭释放。


你可能感兴趣的:(数据库,sqlite,开发,实例)