package activitys; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.nio.channels.FileChannel; import android.app.Activity; import android.content.Context; import android.database.sqlite.SQLiteDatabase; import android.os.AsyncTask; import android.os.Bundle; import android.os.Environment; import android.widget.Toast; class BackupTask extends AsyncTask<String, Void, Integer> { public interface CompletionListener { void onBackupComplete(); void onRestoreComplete(); void onError(int errorCode); } public static final int BACKUP_SUCCESS = 1; public static final int RESTORE_SUCCESS = 2; public static final int BACKUP_ERROR = 3; public static final int RESTORE_NOFILEERROR = 4; public static final String COMMAND_BACKUP = "backupDatabase"; public static final String COMMAND_RESTORE = "restoreDatabase"; private Context mContext; private CompletionListener listener; public BackupTask(Context context) { super(); mContext = context; } public void setCompletionListener(CompletionListener aListener) { listener = aListener; } @Override protected Integer doInBackground(String... params) { File dbFile = mContext.getDatabasePath("mydb"); File exportDir = new File(Environment.getExternalStorageDirectory(), "myAppBackups"); if (!exportDir.exists()) { exportDir.mkdirs(); } File backup = new File(exportDir, dbFile.getName()); String command = params[0]; if (command.equals(COMMAND_BACKUP)) { try { backup.createNewFile(); fileCopy(dbFile, backup); return BACKUP_SUCCESS; } catch (IOException e) { return BACKUP_ERROR; } } else if (command.equals(COMMAND_RESTORE)) { try { if (!backup.exists()) { return RESTORE_NOFILEERROR; } dbFile.createNewFile(); fileCopy(backup, dbFile); return RESTORE_SUCCESS; } catch (IOException e) { return BACKUP_ERROR; } } else { return BACKUP_ERROR; } } @Override protected void onPostExecute(Integer result) { switch (result) { case BACKUP_SUCCESS: if (listener != null) { listener.onBackupComplete(); } break; case RESTORE_SUCCESS: if (listener != null) { listener.onRestoreComplete(); } break; case RESTORE_NOFILEERROR: if (listener != null) { listener.onError(RESTORE_NOFILEERROR); } break; default: if (listener != null) { listener.onError(BACKUP_ERROR); } } } private void fileCopy(File source, File dest) throws IOException { FileChannel inChannel = new FileInputStream(source).getChannel(); FileChannel outChannel = new FileOutputStream(dest).getChannel(); try { inChannel.transferTo(0, inChannel.size(), outChannel); } finally { if (inChannel != null) inChannel.close(); if (outChannel != null) outChannel.close(); } } }
package activitys; import com.example.design_activitys.R; import android.app.Activity; import android.database.sqlite.SQLiteDatabase; import android.os.Bundle; import android.os.Environment; import android.widget.Toast; public class BackupActivity extends Activity implements BackupTask.CompletionListener { @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); SQLiteDatabase db = openOrCreateDatabase("mydb", Activity.MODE_PRIVATE, null); db.close(); } @Override public void onResume() { super.onResume(); if (Environment.getExternalStorageState().equals( Environment.MEDIA_MOUNTED)) { BackupTask task = new BackupTask(this); task.setCompletionListener(this); task.execute(BackupTask.COMMAND_RESTORE); } } @Override public void onPause() { super.onPause(); if (Environment.getExternalStorageState().equals( Environment.MEDIA_MOUNTED)) { BackupTask task = new BackupTask(this); task.execute(BackupTask.COMMAND_BACKUP); } } @Override public void onBackupComplete() { Toast.makeText(this, "Backup Successful", Toast.LENGTH_SHORT).show(); } @Override public void onError(int errorCode) { if (errorCode == BackupTask.RESTORE_NOFILEERROR) { Toast.makeText(this, "No Backup to Restore", Toast.LENGTH_SHORT) .show(); } else { Toast.makeText(this, "Error: " + errorCode, Toast.LENGTH_SHORT) .show(); } } @Override public void onRestoreComplete() { Toast.makeText(this, "Restore Successful", Toast.LENGTH_SHORT).show(); } }
private class DownloadFilesTask extends AsyncTask<URL, Integer, Long> { protected Long doInBackground(URL... urls) { int count = urls.length; long totalSize = 0; for (int i = 0; i < count; i++) { totalSize += Downloader.downloadFile(urls[i]); publishProgress((int) ((i / (float) count) * 100)); // Escape early if cancel() is called if (isCancelled()) break; } return totalSize; } protected void onProgressUpdate(Integer... progress) { setProgressPercent(progress[0]); } protected void onPostExecute(Long result) { showDialog("Downloaded " + result + " bytes"); } }
实现AsyncTask中定义的下面一个或几个方法:
* onPreExecute(), 该方法将在执行实际的后台操作前被UI 线程调用。可以在该方法中做一些准备工 作,如在界面上显示一个进度条,或者一些控件的实例化,这个方法可以不用实现。
* doInBackground(Params...), 将在onPreExecute 方法执行后马上执行,该方法运行在后台线程中。这里将主要负责执行那些很耗时的后台处理工作。可以调用 publishProgress方法来更新实时的任务进度。该方法是抽象方法,子类必须实现。
* onProgressUpdate(Progress...),在publishProgress方法被调用后,UI 线程将调用这个方法从而在界面上展示任务的进展情况,例如通过一个进度条进行展示。
* onPostExecute(Result), 在doInBackground 执行完成后,onPostExecute 方法将被UI 线程调用,后台的计算结果将通过该方法传递到UI 线程,并且在界面上展示给用户.
* onCancelled(),在用户取消线程操作的时候调用。在主线程中调用onCancelled()的时候调用。
为了正确的使用AsyncTask类,以下是几条必须遵守的准则:
1) Task的实例必须在UI 线程中创建
2) execute方法必须在UI 线程中调用
3) 不要手动的调用onPreExecute(), onPostExecute(Result),doInBackground(Params...),onProgressUpdate(Progress...)这几个方法,需要在UI线程中实例化这个task来调用。
4) 该task只能被执行一次,否则多次调用时将会出现异常
doInBackground方法和onPostExecute的参数必须对应,这两个参数在AsyncTask声明的泛型参数列表中指定,第一个为 doInBackground接受的参数,第二个为显示进度的参数,第第三个为doInBackground返回和onPostExecute传入的参 数。
//AsyncTask<>的参数类型由用户设定,这里设为三个String
//第一个String代表输入到任务的参数类型,也即是doInBackground()的参数类型
//第二个String代表处理过程中的参数类型,也就是doInBackground()执行过程中的产出参数类型,通过publishProgress()发消息
//传递给onProgressUpdate()一般用来更新界面
//第三个String代表任务结束的产出类型,也就是doInBackground()的返回值类型,和onPostExecute()的参数类型
private class task extends AsyncTask<String, String, String>
AsyncTask 的执行分为四个步骤,每一步都对应一个回调方法,需要注意的是这些方法不应该由应用程序调用,开发者需要做的就是实现这些方法。在任务的执行过程中,这些方法被自动调用。
* onPreExecute() 当任务执行之前开始调用此方法,可以在这里显示进度对话框。
* doInBackground(Params...) 此方法在后台线程 执行,完成任务的主要工作,通常需要较长的时间。在执行过程中可以调用publicProgress(Progress...)来更新任务的进度。
* onProgressUpdate(Progress...) 此方法在主线程 执行,用于显示任务执行的进度。
* onPostExecute(Result) 此方法在主线程 执行,任务执行的结果作为此方法的参数返回
优势:
import java.io.FileInputStream; import java.io.FileOutputStream; import java.nio.ByteBuffer; import java.nio.channels.FileChannel; /** * FileChannel的基本使用。 */ public class AcquireChannel { public static void main(String[] args) throws Exception { // 根据FileOutputStream获得通道FileChannel FileChannel channel = new FileOutputStream("D:/a.txt").getChannel(); // 字节方式写入 channel.write(ByteBuffer.wrap("hello, NIO world in java!".getBytes())); channel.close(); // 根据FileInputStream获得通道FileChannel channel = new FileInputStream("D:/a.txt").getChannel(); // ByteBuffer分配空间,16个字节 // 这里需要知道 byte是1字节, short和char是2字节,int和float是4字节 // long和double是8字节 1byte=8bit 。 基本只是还是必须记住的。 ByteBuffer buff = ByteBuffer.allocate(16); // 字节数组数据装入buff, channel.read(buff); // 反转此缓冲区 buff.flip(); // 逐个输出,因为分配了16,所以输出的时候只能输出hello, NIO world,剩下的 // 因为空间关系被截断。 while(buff.hasRemaining()){ System.out.print((char)buff.get()); } channel.close(); } }
Environment 包含常量:
MEDIA_BAD_REMOVAL
解释:返回getExternalStorageState() ,表明SDCard 被卸载前己被移除
MEDIA_CHECKING
解释:返回getExternalStorageState() ,表明对象正在磁盘检查。
MEDIA_MOUNTED
解释:返回getExternalStorageState() ,表明对象是否存在并具有读/写权限
MEDIA_MOUNTED_READ_ONLY
解释:返回getExternalStorageState() ,表明对象权限为只读
MEDIA_NOFS
解释:返回getExternalStorageState() ,表明对象为空白或正在使用不受支持的文件系统。
MEDIA_REMOVED
解释:返回getExternalStorageState() ,如果不存在 SDCard 返回
MEDIA_SHARED
解释:返回getExternalStorageState() ,如果 SDCard 未安装 ,并通过 USB 大容量存储共享 返回
MEDIA_UNMOUNTABLE
解释:返回getExternalStorageState() ,返回 SDCard 不可被安装 如果 SDCard 是存在但不可以被安装
MEDIA_UNMOUNTED
解释:返回getExternalStorageState() ,返回 SDCard 已卸掉如果 SDCard 是存在但是没有被安装
Environment 常用方法:
方法:getDataDirectory()
解释:返回 File ,获取 Android 数据目录。
方法:getDownloadCacheDirectory()
解释:返回 File ,获取 Android 下载/缓存内容目录。
方法:getExternalStorageDirectory()
解释:返回 File ,获取外部存储目录即 SDCard
方法:getExternalStoragePublicDirectory(String type)
解释:返回 File ,取一个高端的公用的外部存储器目录来摆放某些类型的文件
方法:getExternalStorageState()
解释:返回 File ,获取外部存储设备的当前状态
方法:getRootDirectory()
解释:返回 File ,获取 Android 的根目录