任何软件都离不开数据,离不开对数据的操作,OPhone OS开发也一样。因此今天特地在闲暇之余写一篇OPhone
数据存储的文章和大家分享,也顺便总结一下自己学习OPhone数据存储的知识。
OPhone OS中可供选择的存储方式有SharedPreferences、文件存储、SQLite数据库方式、内容提供器
(Content provider)和网络,下面我们就详细的介绍一下这些存储方式。
一、SharedPreferences
SharedPreferences是OPhone OS提供用来存储一些简单的配置信息的一种机制,例如登陆的用户名和密码,
默认欢迎语。采用键值对的方式存储,可以很方便的读取和存入。
下面我们通过一个实例来了解一下SharedPreferences的存储方式:
首先我们在main.xml文件中定义布局:
其运行效果图如下:
然后在Activity中定义SharedPreferences对象,进行数据的存取操作。
public class Shared extends Activity {
private EditText nameet,passwordet;
private static final String SETTING_INFOS="SETTING_Infos";
private static final String NAME="name";
private static final String PASSWORD="password";
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
nameet=(EditText)findViewById(R.id.nameet);
passwordet=(EditText)findViewById(R.id.passwordet);
SharedPreferences setting = getSharedPreferences(SETTING_INFOS,0);//获取一个
SharedPreferences对象
String name=setting.getString(NAME,"");//取得一个名称为NAME的字符串
String password=setting.getString(PASSWORD,"");//取得一个名称为PASSWORD的字符串
nameet.setText(name);
passwordet.setText(password);
}
public void onStop(){
super.onStop();
SharedPreferences setting= getSharedPreferences(SETTING_INFOS,0);
setting.edit()//调用edit()方法来,启动编辑功能
.putString(NAME,nameet.getText().toString())
//向sharedPreferences中添加一个键值对key=NAME,value是文本输入框的内容
.putString(PASSWORD,passwordet.getText().toString())
.commit();//提交数据
}
}
这样当第一次程序运行的时候当我们关闭程序,文本框中的内容就会自动保存到SharedPreferences中,每
次重新启动程序,都会自动将SharedPreferences中的数据取出来显示在文本框里,从而使文本框能自动显示上
次输入的内容。
注意:Preferences只能在同一个包中使用,不能在不同的包之间使用。
二、文件存储
前面的SharedPreferences存储比较方便,但是只适合存储比较简单的数据。如果存储比较复杂的数据,可
以选择其他的存储方式。先给大家介绍一下文件存储方式。
学过java的都知道java中的I/O程序,OPhone OS提供了openFileInput和openFileOutput方法来读取设备上
的文件。
String FILE_NAME=”tempfile.tmp”;//确定要操作的文件的名称
FileOutputStream fos=openFileOutput(FILE_NAME,Content.MODE_PRIVATE);//初始化
FileInputStream fis=openFileInput(FILE_NAME);//创建写入流
注意:
上述两个方法只支持读取该目录下的文件,读取非其自身目录下的文件将会抛出异常。
调用FileOutputStream时,指定的文件不存在,Android会自动创建它。另外在默认情况下,写入的时候会
覆盖原文件内容,如果想把新写入的内容附加到原文件内容的后面,需要指定其模式为Context.MODE_APPEND.
三、SQLite存储方式
SQLite是OPhone OS所带有的一个标准的数据库,它支持SQL语句,它是一个轻量级的嵌入式数据库。
下面我们举例来说明SQLite存储方式:
首先创建五个按钮,运行效果如下图:
Activity类的内容如下:
public class ActivityMain extends Activity {
OnClickListener listener1 = null;
OnClickListener listener2 = null;
OnClickListener listener3 = null;
OnClickListener listener4 = null;
OnClickListener listener5 = null;
Button button1;
Button button2;
Button button3;
Button button4;
Button button5;
DatabaseHelper mOpenHelper;
private static final String DATABASE_NAME = "dbForTest.db";
private static final int DATABASE_VERSION = 1;
private static final String TABLE_NAME = "diary";
private static final String TITLE = "title";
private static final String BODY = "body";
private static class DatabaseHelper extends SQLiteOpenHelper {
DatabaseHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase db) {
String sql = "CREATE TABLE " + TABLE_NAME + " (" + TITLE
+ " text not null, " + BODY + " text not null " + ");";
Log.i("haiyang:createDB=", sql);
db.execSQL(sql);
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
prepareListener();
initLayout();
mOpenHelper = new DatabaseHelper(this);
}
private void initLayout() {
button1 = (Button) findViewById(R.id.button1);
button1.setOnClickListener(listener1);
button2 = (Button) findViewById(R.id.button2);
button2.setOnClickListener(listener2);
button3 = (Button) findViewById(R.id.button3);
button3.setOnClickListener(listener3);
button4 = (Button) findViewById(R.id.button4);
button4.setOnClickListener(listener4);
button5 = (Button) findViewById(R.id.button5);
button5.setOnClickListener(listener5);
}
private void prepareListener() {
listener1 = new OnClickListener() {
public void onClick(View v) {
CreateTable();
}
};
listener2 = new OnClickListener() {
public void onClick(View v) {
dropTable();
}
};
listener3 = new OnClickListener() {
public void onClick(View v) {
insertItem();
}
};
listener4 = new OnClickListener() {
public void onClick(View v) {
deleteItem();
}
};
listener5 = new OnClickListener() {
public void onClick(View v) {
showItems();
}
};
}
/*
* 重新建立数据表
*/
private void CreateTable() {
SQLiteDatabase db = mOpenHelper.getWritableDatabase();//获得一个SQLiteDatabase实例
String sql = "CREATE TABLE " + TABLE_NAME + " (" + TITLE
+ " text not null, " + BODY + " text not null " + ");";//创建表语
句create
Log.i("haiyang:createDB=", sql);
try {
db.execSQL("DROP TABLE IF EXISTS diary");
db.execSQL(sql);
setTitle("数据表成功重建");
} catch (SQLException e) {
setTitle("数据表重建错误");
}
}
/*
* 删除数据表
*/
private void dropTable() {
SQLiteDatabase db = mOpenHelper.getWritableDatabase();
String sql = "drop table " + TABLE_NAME;
try {
db.execSQL(sql);
setTitle("数据表成功删除:" + sql);
} catch (SQLException e) {
setTitle("数据表删除错误");
}
}
/*
* 插入两条数据
*/
private void insertItem() {
SQLiteDatabase db = mOpenHelper.getWritableDatabase();
String sql1 = "insert into " + TABLE_NAME + " (" + TITLE + ", " + BODY
+ ") values('haiyang', 'android的发展真是迅速啊');";
String sql2 = "insert into " + TABLE_NAME + " (" + TITLE + ", " + BODY
+ ") values('icesky', 'android的发展真是迅速啊');";
try {
Log.i("haiyang:sql1=", sql1);
Log.i("haiyang:sql2=", sql2);
db.execSQL(sql1);
db.execSQL(sql2);
setTitle("插入两条数据成功");
} catch (SQLException e) {
setTitle("插入两条数据失败");
}
}
/*
* 删除其中的一条数据
*/
private void deleteItem() {
try {
SQLiteDatabase db = mOpenHelper.getWritableDatabase();
db.delete(TABLE_NAME, " title = 'haiyang'", null);
setTitle("删除title为haiyang的一条记录");
} catch (SQLException e) {
}
}
/*
* 在屏幕的title区域显示当前数据表当中的数据的条数。
*/
private void showItems() {
SQLiteDatabase db = mOpenHelper.getReadableDatabase();
String col[] = { TITLE, BODY };
Cursor cur = db.query(TABLE_NAME, col, null, null, null, null, null);
Integer num = cur.getCount();
setTitle(Integer.toString(num) + " 条记录");
}
}
四、ContentProvider存储方式
OPhone OS程序主要有四个主要部分:Activity,Broadcast Intent Receiver,Service,Content Provider
。
在android中数据是私有的,解决这种弊端的方式是通过一个Content Provider的抽象接口将自己的数据暴
露给其他程序,外部使用者不用关心数据的存储方式怎样,只需要通过这套接口来对数据操作。
下面列举了几个较常见的接口:
Query(Uri uri,String[] projection,String selection,String[] seledtionArgs,String sortOrder);通过
Uri进行查询,返回一个Cursor。
update(Uri uri,ContentValues values,String where,String[] selectionArgs);更新Uri指定位置的数据
insert(Uri uri,ContentValues values);将一组数据插入到Uri指定的地方
delete(Uri uri,String where,String[] selectionArgs);删除指定Uri并且符合一定条件的数据。
下面我们来介绍一下ContentResolver接口,这个接口可以访问ContentProvider提供的数据,在当前的
Activity中可以通过getContentResolver()可以得到当前应用的ContentResolver实例,这两个接口中需要实
现的方法对应。
在上面提到的Uri形式通常有两种,一种是指定全部数据,另一种是指定某个ID的数据
如:
Content://contacts/people/这个Uri指定全部联系人数据
Content://contacts/people/1这个指定ID是1的联系人的数据
下面举个例子,使用ContentProvider读取系统的数据,这个例子首先在联系人应用中插入一些联系人信息
,然后把这些联系人的名字和电话显示出来。
首先来看一下ActivityMain中的onCreate()方法,代码如下:
public class ActivityMain extends ListActivity {
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);Cursor c = getContentResolver().query
(Phones.CONTENT_URI, null, null, null, null);
//getContentResolver()方法得到一个ContentResolver对象,然后调用方法query
(Phones.CONTENT_URI,null,null,null,null)方法查询所有联系人,并返回一个Cursor
startManagingCursor(c); //让系统管理生成的Cursor
ListAdapter adapter = new SimpleCursorAdapter(this,
android.R.layout.simple_list_item_2, c,
new String[] { Phones.NAME, Phones.NUMBER },
new int[] { android.R.id.text1, android.R.id.text2 });
setListAdapter(adapter);//将ListView和SimpleCursorAdapter进行绑定
}
}
五、网络存储方式
前面四种存储方式都是将数据存储在本地设备上,除此之外,还有一种存储数据的方式,通过网络来实现数
据的存储和获取。如果要掌握网络存储的方式需要熟悉java.net.*,android.net.*两个包的内容。此方法在此就
不再赘述了,有兴趣的读者可以找资料研究一下。