本篇文章主要讲解数据持久化技术的最后一个:SQLite数据库存储中的创建数据库和升级数据库。
序言
前面的文件存储和SharedPreferences存储只适用于保存一些简单的数据和键值对,当需要存储大量复杂的关系型数据的时候,如:手机的短信中可能会有多个会话,而每个会话又包含多个信息内容。这时使用数据库就可做到,要想使用SQLite数据库需要SQL的一些基础知识。
SQLite介绍
SQLite是一款轻量级的关系型数据库,运算速度快,占用资源少,比一般数据库简单,Android把这个功能内置到了系统中,使得数据持久化的功能有了质的飞跃。 SQLite是目前最流行的开源嵌入式数据库,SQLite可以很好的支持关系型数据库所具备的一些基本特征,如标准SQL语法、事务、数据表和索引等。SQLite支持 NULL、INTEGER、REAL(浮点数字)、TEXT(字符串文本)和BLOB(二进制对象)数据类型,虽然它支持的类型虽然只有五种,但实际上sqlite3也接受varchar(n)、char(n)、decimal(p,s) 等数据类型,只不过在运算或保存时会转成对应的五种数据类型。下面我们将列举一下SQLite的主要特征:
- 1). 管理简单,甚至可以认为无需管理。
- 2). 操作方便,SQLite生成的数据库文件可以在各个平台无缝移植。
- 3). 可以非常方便的以多种形式嵌入到其他应用程序中,如静态库、动态库等。
- 4). 易于维护。
SQLiteOpenHepler介绍
SQLiteOpenHelper帮助类是一个抽象类,可以简单地对数据库进行创建和升级,能够更加方便地管理数据库。其有两个抽象方法,分别是onCreate()和onUpgrade(),必须在自己的帮助类里重写这两个方法,然后分别在这两个方法中去实现创建、升级数据库的逻辑。
SQLiteOpenHepler有两个重要的实例方法:getReadableDatabase()和getWritableDatabase()。这两个方法都可以创建或打开一个现有的数据库,并返回一个可对数据库进行读写操作的对象。不同的是当数据库不可写入时,getReadableDatabase()返回的对象将以只读的方式打开数据库,而getWritableDatabase()出现异常。
SQLiteOpenHepler构造方法有4个参数,第一个是Context;第二个是数据库名;第三个允许我们在查询数据的时候返回一个自定义的Cursor,一般传入null;第四个表示当前数据库的版本号,可用于对数据库升级。
一、创建数据库
下面将尝试一下SQLiteOpenHepler的用法。
新建项目:DatabaseTest。
新建MyDatabaseHelper类,代码如下:
首先把建表语句定义为字符串常量,然后在onCreate()方法中又调用execSQL()方法去执行这条语句。
public class MyDatabaseHelper extends SQLiteOpenHelper {
public static final String CREATE_BOOK = "create table Book ("
+ "id integer primary key autoincrement, "
+ "author text, "
+ "price real, "
+ "pages integer, "
+ "name text)";
private Context mContext;
public MyDatabaseHelper(Context context, String name,
SQLiteDatabase.CursorFactory factory, int version) {
super(context, name, factory, version);
mContext = context;
}
@Override
public void onCreate(SQLiteDatabase db) {
db.execSQL(CREATE_BOOK);
Toast.makeText(mContext, "Create succeeded", Toast.LENGTH_SHORT).show();
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
}
修改布局文件activity_main.xml的代码,如下:
加入一个创建数据库的按钮。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http:///apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<Button
android:id="@+id/create_database"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Create database"
/>
</LinearLayout>
最后修改MainActivity中的代码,如下:
在onCreate()方法中,构建了一个MyDatabaseHelper对象,并通过构造函数的参数将数据库名指定为BookStore.db,版本号为1,然后在按钮的点击事件里调用getWritableDatabase()方法,即可创建数据库。
public class MainActivity extends AppCompatActivity {
private MyDatabaseHelper dbHelper;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
dbHelper = new MyDatabaseHelper(this, "BookStore.db", null, 1);
Button createDatabase = (Button) findViewById(R.id.create_database);
createDatabase.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
dbHelper.getWritableDatabase();
}
});
}
}
效果 如下:
点击按钮,弹出信息,再次点击不会弹出了,因为不会再创建一次。
二、升级数据库
MyDatabaseHelper中还有一个空方法,onUpgrade()方法是用于对数据库升级的。
下面再加一张Catagory表。
添加到MyDatabaseHelper中,代码如下:
这时候如果像上面的创建数据库一样,会失败!因为BookStore.db数据库已经存在,点击按钮,MyDatabaseHelper中的onCreate方法不会执行。
解决上述问题很简单,只需巧妙地运用SQLiteOpenHelper的升级功能可以解决这个问题,在onUpgrdae()方法中执行DROP语句,先将已经存在的表删掉。接下来去修改MainActivity中的代码,让onUpgrdae()方法执行。
public class MyDatabaseHelper extends SQLiteOpenHelper {
public static final String CREATE_BOOK = "create table Book ("
+ "id integer primary key autoincrement, "
+ "author text, "
+ "price real, "
+ "pages integer, "
+ "name text)";
public static final String CREATE_CATEGORY = "create table Category ("
+ "id integer primary key autoincrement, "
+ "category_name text, "
+ "category_code integer)";
private Context mContext;
public MyDatabaseHelper(Context context, String name,
SQLiteDatabase.CursorFactory factory, int version) {
super(context, name, factory, version);
mContext = context;
}
@Override
public void onCreate(SQLiteDatabase db) {
db.execSQL(CREATE_BOOK);
db.execSQL(CREATE_CATEGORY);
Toast.makeText(mContext, "Create succeeded", Toast.LENGTH_SHORT).show();
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("drop table if exists Book");
db.execSQL("drop table if exists Category");
onCreate(db);
}
}
MainActivity代码如下:
只修改了一句代码,在创建MyDatabaseHelper实例时,传入的第四个参数是版本号,将1修改成比1大的数,就可以让onUpgrade()方法执行了。
public class MainActivity extends AppCompatActivity {
private MyDatabaseHelper dbHelper;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
dbHelper = new MyDatabaseHelper(this, "BookStore.db", null, 2);
Button createDatabase = (Button) findViewById(R.id.create_database);
createDatabase.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
dbHelper.getWritableDatabase();
}
});
}
}
效果如下:
点击按钮后,再次弹出提升。
本篇文章先到这里,目前我们已经学会了数据库的创建和升级,下面将要学习数据库的CRUD(增删改查)操作。