常用的建立数据库的方法,即在代码中进行对数据库的建立。在程序运行过程中,当程序需要进行数据库操作时,应用程序会首先尝试打开数据库,此时如果数据库并不存在,程序则会自动建立数据库,然后再打开数据库。在编程实现时,一般将所有对数据库的操作都封装在类中,因此只要调用这个类,就可以完成对数据库的添加、更新、删除和查询等操作。下面我们就来介绍一些常用的接口和类。
本文主要介绍一下如何通过SQLiteOpenHelper类来实现建立数据库。
SQLiteOpenHelper是一个抽象的辅助类(Helper),用来打开(若数据库已存在)或创建数据库。当在程序当中调用SQLiteOpenHelper的getWritableDatabase()方法,或者getReadableDatabase()方法的时候,这两个方法根据数据库是否存在、版本号和是否可写等情况,决定在返回数据库对象前是否需要建立数据库,如果当时没有数据,那么Android系统就会自动生成一个数据库。关于抽象类我们都知道,如果要使用它,一定是继承它。所以使用它都是通过自己定义一个类继承于它并实现其抽象方法:onCreate(SQLiteDatabase),onUpgrade(SQLiteDatabase, int, int),onOpen(SQLiteDatabase)3个方法,如表7-6所示。
表7-6 SQLiteOpenHelper类中重要方法
方法 |
描述 |
onCreate(SQLiteDatabase) |
在数据库第一次生成的时候会调用这个方法,一般在这个方法里边生成数据库表 |
onUpgrade(SQLiteDatabase,int,int) |
当数据库需要升级的时候,Android系统会主动地调用这个方法。一般在这个方法里边删除数据表,并建立新的数据表,当然是否还需要做其他的操作,完全取决于应用的需求 |
onOpen(SQLiteDatabase) |
这是当打开数据库时的回调函数,一般也不会用到 |
下面通过对DBAdapter封装类的代码来学习如何通过继承SQLiteOpenHelper类来实现数据库的建立、打开和关闭等操作。
代码清单7-34 DBAdapter
public class DBAdapter {
//声明了数据库的基本信息
//数据库文件的名称
private static final String DB_NAME = "people.db";
//数据库表格名称和数据库版本
private static final String DB_TABLE = "peopleinfo";
private static final int DB_VERSION = 1;
//数据库表中的属性名称
public static final String KEY_ID = "_id";
public static final String KEY_NAME = "name";
public static final String KEY_AGE = "age";
public static final String KEY_HEIGHT = "height";
//声明SQLiteDatabase对象db
private SQLiteDatabase db;
private final Context context;
//DBOpenHelper继承了SQLiteOpenHelper,声明DBOpenHelper类对象,
//辅助建立、更新和打开数据库
private DBOpenHelper dbOpenHelper;
private static class DBOpenHelper extends SQLiteOpenHelper {}
public DBAdapter(Context _context) {
context = _context;
}
//调用了SQLiteOpenHelper类的getWritableDatabase()方法和getReadableDatabase()方法,打开数据库
public void open() throws SQLiteException {
dbOpenHelper = new DBOpenHelper(context, DB_NAME, null, DB_VERSION);
try {
//负责得到一个可写的SQLite数据库,如果这个数据库还没有
//建立,那么mOpenHelper辅助类负责建立这个数据库。如果数
//据库已经建立,那么直接返回一个可写的数据库
db = dbOpenHelper.getWritableDatabase();
}catch (SQLiteException ex) {
db = dbOpenHelper.getReadableDatabase();
}
}
public void close() {
if (db != null){
//关闭数据库
db.close();
db = null;
}
}
}
如代码清单7-34所示,我们注意到,在声明了数据库基本信息后,紧接着声明了SQLiteDatabase对象db。这里的SQLiteDatabase类是由Android提供的封装了一些数据库操作的API的类,使用该类可以完成对数据进行添加(Create)、查询(Retrieve)、更新(Update)和删除(Delete)操作(这些操作简称为CRUD),执行SQL命令,对数据进行管理等工作。在下一节的数据操作中,将对使用该类实现数据操作进行具体讲解。
之前有讲解到,继承SQLiteOpenHelper类覆盖其抽象方法,这里来覆盖onCreate(SQLiteDatabase db)和onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion)。为了实现对数据库进行管理,重载onCreate()方法和onUpgrade()方法的代码如代码清单7-35所示。
代码清单7-35 DBOpenHelper
private static class DBOpenHelper extends SQLiteOpenHelper {
public DBOpenHelper(Context context, String name,
CursorFactory factory, int version){
super(context, name, factory, version);
}
private static final String DB_CREATE = "create table " + DB_TABLE +
"("+KEY_ID+" integer primary key autoincrement, "+
KEY_NAME+" text not null, "+KEY_AGE+" integer,"+
KEY_HEIGHT + " float);";
@Override
public void onCreate(SQLiteDatabase _db) {
db.execSQL(DB_CREATE);
}
@Override
public void onUpgrade(SQLiteDatabase _db, int _oldVersion, int _newVersion) {
_db.execSQL("DROP TABLE IF EXISTS " + DB_TABLE);
onCreate(_db);
}
}
在上述代码中,在声明了创建表的SQL命令语DB_CREATE之后,分别重载了onCreate()方法和onUpgrade()方法,这是继承SQLiteOpenHelper类必须重载的两个方法。
onCreate()方法在数据库第一次建立时被调用,一般用来创建数据库中的表,并做适当的初始化工作,在onCreate()方法中,通过调用SQLiteDatabase对象的execSQL()方法,执行创建表的SQL命令。
onUpgrade()方法在数据库需要升级时被调用,一般用来删除旧的数据库表,并将数据转移到新版本的数据库表中。为了简单起见,在本段代码的onUpgrade()方法中,并没有做任何的数据转移,而仅仅删除原有的表后建立新的数据库表。
程序开发人员不应直接调用onCreate()和onUpgrade()方法,而应该由SQLiteOpenHelper类来决定何时调用这两个方法。SQLiteOpenHelper类的getWritableDatabase()方法和getReadableDatabase()方法是可以直接调用的方法。getWritableDatabase()方法用来建立或打开可读/写的数据库对象,一旦方法调用成功,数据库对象将被缓存,何时需要使用数据库对象,都可以调用这个方法获取到数据库对象,但一定要在不使用时调用close()方法关闭数据库。如果保存数据库文件的磁盘空间已满,调用getWritableDatabase()方法则无法获得可读/写的数据库对象,这时可以调用getReadableDatabase()方法,获得一个只读的数据库对象。
如果程序开发人员不希望使用SQLiteOpenHelper类,同样可以通过SQLiteDatabase对象直接创建数据库。通过SQLiteDatabase(android.database.sqlite.SQLiteDatabase)这个类,除了可以实现数据库的创建或打开以外,还可以进行创建表、插入数据、删除数据、查询数据、修改数据等操作,如表7-7所示。
表7-7 SQLiteDatabase类中重要方法
方法 |
描述 |
public static SQLiteDatabase openOrCreateDatabase(String path,SQLiteDatabase.CursorFactory factory) |
用于打开或创建一个数据库(对于sqlite来说,就是打开或产生一个数据库文件),参数中的File类就是java中表示系统文件路径的File类,而SQLiteDatabase.CursorFactory则是一个产生Cursor对象的工厂类 |
public long insert (String table, String nullColumnHack, ContentValues values) |
用于在数据库中加入数据。ContentValue类似于java中HashMap类,用于以键值对的方式保存数据 |
public int delete (String table, String whereClause, String[] whereArgs) |
删除表中的数据 |
public Cursor query (booleandistinct, String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy, String limit) |
查询数据库中的数据 |
public int update (String table, ContentValues values, String whereClause, String[] whereArgs) |
用于修改数据 |
public void execSQL (String sql) |
执行String表示的非查询的SQL语句,例如Create等 |
public void close () |
用来关闭数据库并释放数据库占用的相关资源 |
通过SQLiteDatabase对象直接创建数据库方法如下:首先调用openOrCreateDatabases()方法创建数据库对象,然后执行SQL命令建立数据库中的表和直接的关系。示例代码如代码清单7-36所示。
代码清单7-36 openOrCreateDatabases()方法创建数据库对象
private static final String DB_CREATE = "create table " +
DB_TABLE + " (" + KEY_ID + " integer primary key autoincrement, " +
KEY_NAME+ " text not null, " + KEY_AGE+ " integer, " + KEY_HEIGHT + " float); ";
public void create() {
db.openOrCreateDatabases(DB_NAME, context.MODE_PRIVATE, null)
db.execSQL(DB_CREATE);