`
tmj_159
  • 浏览: 707440 次
  • 性别: Icon_minigender_1
  • 来自: 永州
社区版块
存档分类
最新评论

上官网学android之七(Saving Data)

 
阅读更多

官网链接

http://developer.android.com/training/basics/data-storage/index.html

 

一、保存key-value集

key-value 对广大coder来说已经再熟悉不过了。

为了方便使用者快捷的存取数据在andorid中key-value保存在一个文件中的。1.1 获取SharedPreferences实例

在Activity中可以直接获得SharedPreferences实例,否则需要先得到Activity实例

 

SharedPreferences preferences = getPreferences(Context.MODE_PRIVATE);

SharedPreferences sharedPreferences = getSharedPreferences(
				"sharedFile", Context.MODE_PRIVATE);

 两种方式有区别,之前不是说这些key-value数据存放在文件中吗,所以getPreferences是当前Activity实例的一个文件,而getSharedPreference是新建一个文件来存,所以需要提供一个名字。

第二个参数是模式的选择的,简单说点,MODE_PRIVATE是私有的,不给其它使用,还有比如MODE_WORLD_WRITEABLE则可以全局访问,据官网介绍甚至其它APP都可以使用哦,这个没有尝试。

 

1.2 读和写

很简单的API所以放一起写了,直接上代码

SharedPreferences preferences = getPreferences(Context.MODE_PRIVATE);
preferences.edit().putString("key", "test").commit();
String ret0=preferences.getString("key", "default");
System.out.println("key -------------- " + ret0);

SharedPreferences sharedPreferences = getSharedPreferences(
				"sharedFile", Context.MODE_PRIVATE);
sharedPreferences.edit().putString("key", "testShare").commit();
String ret = sharedPreferences.getString("key", "default");
System.out.println("shared key ------------- " + ret);

 注意到了吗,是写System.out来输出的,通常android不用这种输出方式,因为文章还没有介绍到如何利用android的Log API来现实日志,所以先用着吧。

 

 

二、保存文件

 

2.1 选择内部还是外部的存储介质

 

 所谓内存储是指机器本来的内存,我们通常叫机身内存。外部存储介质比如SD卡之类的。

为什么分为两部分呢,因为

在内部存储:

1.总是可用的

2.保存的文件通常只能它自己的APP可以访问

3.卸载APP的时候会连带删除APP的文件

 

外部存储

1.不总是肯定,因为在某些时候你可能取出SD卡

2.因为是全局可读的,所以保存在这里的文件可能会在你的控制之外。

3.卸载APP的时候,系统会删除你用getExternalFilesDir()保存的文件,其它方式保存的不会删除。

 

 2.2 为外部存储设置权限

我们通过在Manifest 文件中设置外部存储的权限

 

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="cn.tang.test"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    ......
</manifest>
 这是写的权限,如果是读权限 WRITE_EXTERNAL_STORAGE

 

 

2.3 在内部存储中保存文件

 

可以通过以下两种方式来得到一个文件

getFilesDir()

getCacheDir() 临时的缓存文件,系统内存不够时,可能会删除

//context.getFilesDir()
File file = new File(context.getFilesDir(), filename);

//context.getCacheDir()
 File file;
    try {
        String fileName = Uri.parse(url).getLastPathSegment();
        file = File.createTempFile(fileName, null, context.getCacheDir());
    catch (IOException e) {
        // Error while creating file
    }
    return file;

 向文件写数据利用到了文件流

String filename = "myfile";
String string = "Hello world!";
FileOutputStream outputStream;

try {
  outputStream = openFileOutput(filename, Context.MODE_PRIVATE);
  outputStream.write(string.getBytes());
  outputStream.close();
} catch (Exception e) {
  e.printStackTrace();
}

 

 

2.4 在外部存储中保存文件

因为外部存储不一定总可用,所以我们需要判断可用的情况

/* Checks if external storage is available for read and write */
public boolean isExternalStorageWritable() {
    String state = Environment.getExternalStorageState();
    if (Environment.MEDIA_MOUNTED.equals(state)) {
        return true;
    }
    return false;
}

/* Checks if external storage is available to at least read */
public boolean isExternalStorageReadable() {
    String state = Environment.getExternalStorageState();
    if (Environment.MEDIA_MOUNTED.equals(state) ||
        Environment.MEDIA_MOUNTED_READ_ONLY.equals(state)) {
        return true;
    }
    return false;
}

尽管在外部存储中的文件可以被用户和其它APP修改,android提供了两种类型的文件。

Public files 卸载APP后文件不会删除,比如照片信息

private files 卸载之后文件被删除,比如说额外的下载的资源文件

//公有的文件
public File getAlbumStorageDir(String albumName) {
    // Get the directory for the user's public pictures directory. 
    File file = new File(Environment.getExternalStoragePublicDirectory(
            Environment.DIRECTORY_PICTURES), albumName);
    if (!file.mkdirs()) {
        Log.e(LOG_TAG, "Directory not created");
    }
    return file;
}
//私有的文件
public File getAlbumStorageDir(Context context, String albumName) {
    // Get the directory for the app's private pictures directory. 
    File file = new File(context.getExternalFilesDir(
            Environment.DIRECTORY_PICTURES), albumName);
    if (!file.mkdirs()) {
        Log.e(LOG_TAG, "Directory not created");
    }
    return file;
}

2.5 查询空闲空间

在程序运行时知道空闲空间在某些情况下可能会很有用,必须你下载一个较大文件的时候

android提供两个方法

getFreeSpace()

getTotalSpace()

 

2.6 删除一个文件

myFile.delete();
myContext.deleteFile(fileName);

当app被卸载的时候,系统会按照下面的逻辑删除文件

1. 删除internal storage(内部存储)中保存的文件

2. 删除extenal storage(外部存储)中使用getExternalFilesDir()保存的文件

 

三、保存到数据库中

android有内嵌的数据库sqlite。

官网的文档关于这方面写的感觉有点啰嗦了,可能想让大家养成一个好的习惯吧。其实有超级简单的例子,可能在现阶段有些人还不想搞那么复杂来个简单的吧,我直接在Activity中写一个方法,然后再onCreate中调用它测试了一下。

 

private void dbtest() {
		SQLiteDatabase db = openOrCreateDatabase("my.db", Context.MODE_PRIVATE,
				null);
		db.execSQL("drop table if exists test");
		db.execSQL("create table test(id varchar,name varchar)");
		db.execSQL("insert into test values(?,?)", new Object[] { "id_1", "name_1" });

		Cursor cursor = db.rawQuery("select * from test where name =?",
				new String[] { "name_1" });
		while (cursor.moveToNext()) {
			String id = cursor.getString(cursor.getColumnIndex("id"));
			System.out.println("id =========== " + id);
			Log.i("db_target", "id \t" + id);
		}
		cursor.close();

		db.close();
	}
 爽了一下之后开始跟着官网慢慢来吧。

 

 

3.1 定义Schema 和 Contract

所谓schema和Contract 其实是你的数据库和表的定义,他们叫的比较专业,我等通常叫创建数据库和表。

哎,谁谁谁,给创建的sql语句给我发一份....

 

public final class FeedReaderContract {

	public FeedReaderContract() {}
	
	public static abstract class FeedEntry implements BaseColumns {
        public static final String TABLE_NAME = "entry";
        public static final String COLUMN_NAME_ENTRY_ID = "entryid";
        public static final String COLUMN_NAME_TITLE = "title";
        public static final String COLUMN_NAME_SUBTITLE = "subtitle";
    }
}
 理解为常量类,类中定义了一些数据库定义方面的常量。

 

 

3.2 使用SQL Helper 创建数据库

android提供了一个叫做SQLiteOpenHelper的类来帮助我们使用SQLite.

 

public class FeedReaderDbHelper extends SQLiteOpenHelper {
	public static final int DATABASE_VERSION = 1;
	public static final String DATABASE_NAME = "FeedReader.db";

	public FeedReaderDbHelper(Context context) {
		super(context, DATABASE_NAME, null, DATABASE_VERSION);
	}

	@Override
	public void onCreate(SQLiteDatabase db) {
		db.execSQL(SQL_CREATE_ENTRIES);
	}

	@Override
	public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
		db.execSQL(SQL_DELETE_ENTRIES);
        onCreate(db);
	}

	private static final String TEXT_TYPE = " TEXT";
	private static final String COMMA_SEP = ",";
	private static final String SQL_CREATE_ENTRIES = "CREATE TABLE "
			+ FeedEntry.TABLE_NAME + " (" + FeedEntry._ID
			+ " INTEGER PRIMARY KEY," + FeedEntry.COLUMN_NAME_ENTRY_ID
			+ TEXT_TYPE + COMMA_SEP + FeedEntry.COLUMN_NAME_TITLE + TEXT_TYPE
			+ COMMA_SEP + " )";

	private static final String SQL_DELETE_ENTRIES = "DROP TABLE IF EXISTS "
			+ FeedEntry.TABLE_NAME;

}
 根据以前的常量值,在这个类中,拼写了一些常用的SQL语句,为了方便看我放在了最后面。继承SQLiteOpenHelper之后,需要实现onCreate()和onUpdate()方法,这两个方法分别在第一次使用数据库时,和版本号改变后调用,所谓版本号改动就是DATABASE_VERSION值改变了,如果你的APP数据库表发生改变了,修改下这个版本号,系统在下次启动的时候会调用onUpdate()方法,然后我们在方法中做一些适应性的改变,上面例子中比较暴力,直接把以前的表删除了,建的新表。(对于这种情况我表示有点害怕,出问题别怪我,官网上就这么写的)

 

 

3.3 put/read/delete/update

 

增删该查,数据库四大神兵,必须得知道的

 

private void dbOperationTest() {
		FeedReaderDbHelper mDbHelper = new FeedReaderDbHelper(this);
		SQLiteDatabase wdb = mDbHelper.getWritableDatabase();
		SQLiteDatabase rdb = mDbHelper.getReadableDatabase();

		// put
		ContentValues values = new ContentValues();
		values.put(FeedEntry.COLUMN_NAME_ENTRY_ID, "id_" + 0);
		values.put(FeedEntry.COLUMN_NAME_TITLE, "title_" + 0);

		long newRowId;
		newRowId = wdb.insert(FeedEntry.TABLE_NAME, null, values);

		// query
		Cursor cursor = rdb.query(FeedEntry.TABLE_NAME, // The table to query
				new String[] { FeedEntry.COLUMN_NAME_ENTRY_ID,
						FeedEntry.COLUMN_NAME_TITLE }, // The columns to return
				FeedEntry.COLUMN_NAME_TITLE +"=?", // The columns for the WHERE clause
				new String[]{"title_"+0}, // The values for the WHERE clause
				null, // don't group the rows
				null, // don't filter by row groups
				FeedEntry.COLUMN_NAME_TITLE+" DESC" // The sort order
				);
		while (cursor.moveToNext()) {
			String id = cursor.getString(cursor.getColumnIndex(FeedEntry.COLUMN_NAME_ENTRY_ID));
			Log.i("db_target", "id \t" + id);
		}
		cursor.close();
		
		//delete
		String selection = FeedEntry.COLUMN_NAME_ENTRY_ID + " LIKE ?";
		String[] selectionArgs = { "id_"+0 };
		wdb.delete(FeedEntry.TABLE_NAME, selection, selectionArgs);
		
		//udpate
		ContentValues updateValues = new ContentValues();
		values.put(FeedEntry.COLUMN_NAME_TITLE, "title_2");

		int count = wdb.update(
			    FeedEntry.TABLE_NAME,
			    updateValues,
			    selection,
			    selectionArgs);
		
		//close
		rdb.close();
		wdb.close();
	}

 

 
 
 
 

 

 

 

分享到:
评论

相关推荐

    Saving Data on Android - v1.zip

    《Saving Data on Android》是针对Android开发人员的一份宝贵资源,特别关注于在Android平台上保存数据的方法。这个压缩包包含了三种格式的文档——PDF、ePub以及源代码,旨在帮助开发者深入理解如何在Swift服务器端...

    Android学习笔记-保存数据到SQL数据库中(Saving Data in SQL Databases)

    上篇文章学习了android保存文件,今天学习的是保存数据到SQL数据库中。相信大家对数据库都不陌生。对于大量重复的,有特定结构的数据的保存,用 SQL数据库 来保存是最理想不过了。 下面将用一个关于联系人的数据库...

    android sdk 自带 实例(samples)

    A simple example that illustrates a few different ways for an application to implement support for the Android data backup and restore mechanism. Bluetooth Chat An application for two-way text ...

    Android Application Security Essentials

    Saving user data 23 Service 23 Service declaration 24 Service modes 25 Lifecycle management 26 Binder 28 Content Provider 29 Provider declaration 30 Other security consideration 33 Table of Contents ...

    Android 下载图片保存到相册

    在Android平台上,下载图片并保存到用户设备的相册是一项常见的功能。这通常涉及到网络请求、文件操作以及与系统媒体库的交互。以下是对`Android 下载图片保存到相册`这一主题的详细讲解。 首先,我们需要理解...

    Android集成高德定位

    在Android应用开发中,集成高德地图API进行定位是常见的需求。高德地图SDK提供了丰富的定位服务,包括实时定位、单次定位以及多种定位模式。本文将深入探讨如何在Android项目中集成高德定位,以实现高效且准确的地理...

    android 基于百度定位

    在Android应用开发中,集成百度地图API进行定位是常见的需求,尤其对于提供地理位置服务的应用来说至关重要。本项目“android基于百度定位”旨在演示如何在Android应用程序中实现这一功能。通过学习这个实例,开发者...

    Android代码-bridge

    In spite of warnings from the Android development team stating that the state restoration framework should only be used for small amounts of view-related data, many developers have found it very ...

    developing android application with adobe air.part1

    Chapter 6 : Opening and Closing an Application and Saving Data The AIR Application Why and How to Save Data Conclusion Chapter 7 : Multitouch Technology A Brief History What Is Multitouch and Gesture?...

    Android调用百度地图

    在Android开发中,集成外部应用服务是常见的需求之一,其中百度地图API的使用就是一个典型的例子。本教程将详细讲解如何在Android应用中调用百度地图,并实现Activity和Fragment中的定位功能。 首先,我们需要在...

    CommonsWare.The.Busy.Coders.Guide.to.Android.Development.Version.8.2.2017

    Android, the next-generation open mobile platform from Google and the Open Handset Alliance, is poised to become a significant player in the mobile device market. The Android platform gives developers...

    developing android application with adobe air.part4.rar

    Chapter 6 : Opening and Closing an Application and Saving Data The AIR Application Why and How to Save Data Conclusion Chapter 7 : Multitouch Technology A Brief History What Is Multitouch and Gesture?...

    developing android application with adobe air.part2.rar

    Chapter 6 : Opening and Closing an Application and Saving Data The AIR Application Why and How to Save Data Conclusion Chapter 7 : Multitouch Technology A Brief History What Is Multitouch and Gesture?...

    developing android application with adobe air.part3.rar

    Chapter 6 : Opening and Closing an Application and Saving Data The AIR Application Why and How to Save Data Conclusion Chapter 7 : Multitouch Technology A Brief History What Is Multitouch and Gesture?...

    Professional Android 4 Application Development 源代码

    Chapter 1: Hello, Android A Little Background What Android Isn't Android: An Open Platform for Mobile Development Native Android Applications Android SDK Features Introducing the Open Handset Alliance...

    基于android高德地图开发

    在Android平台上进行应用程序开发时,高德地图API是一个强大的工具,它为开发者提供了丰富的地图功能,如定位、导航、路线规划、附近搜索等。本文将深入探讨如何在Android项目中集成高德地图,并实现基本的定位和...

Global site tag (gtag.js) - Google Analytics