Android 使用 AsyncTask 来下载图片
2013-01-31 21:56
447 查看
Android使用AsyncTask有如下好处:
1.线程的开销较大,如果每个任务都要创建一个线程,那么应用程序的效率要低很多;
2.线程无法管理,匿名线程创建并启动后就不受程序的控制了,如果有很多个请求发送,那么就会启动非常多的线程,系统将不堪重负;
3.另外,在新线程中更新UI还必须要引入handler,这让代码看上去非常臃肿;
为了解决这一问题,Android在1.5版本引入了AsyncTask.AsyncTask的特点是任务在主线程之外运行,而回调方法是在主线程中执行,这就有效地避免了使用Handler带来的麻烦。阅读AsyncTask的源码可知,AsyncTask是使用java.util.concurrent框架来管理线程以及任务的执行的,concurrent框架是一个非常成熟,高效的框架,经过了严格的测试。这说明AsyncTask的设计很好的解决了匿名线程存在的问题。
AsyncTask定义了三种泛型类型Params,Progress和Result.
Params启动任务执行的输入参数,比如HTTP请求的URL;
Progress后台任务执行的百分比;
Result后台执行任务最终返回的结果,比如String;
子类必须实现抽象方法doInBackground(Params…p),在此方法中实现任务的执行工作,比如连接网络获取数据等。通常还应该实现onPostExecute(Resultr)方法,因为应用程序关心的结果在此方法中返回。需要注意的是AsyncTask一定要在主线程中创建实例。
AsyncTask的执行分为四个步骤,每一步都对应一个回调方法,需要注意的是这些方法不应该由应用程序调用,开发者需要做的就是实现这些方法。在任务的执行过程中,这些方法被自动调用,运行过程,
onPreExecute()当任务执行之前开始调用此方法,可以在这里显示进度对话框。
doInBackground(Params…)此方法在后台线程执行,完成任务的主要工作,通常需要较长的时间。在执行过程中可以调用publicProgress(Progress…)来更新任务的进度。
onProgressUpdate(Progress…)此方法在主线程执行,用于显示任务执行的进度。
onPostExecute(Result)此方法在主线程执行,任务执行的结果作为此方法的参数返回。
viewsource
print?
在开发Android应用时必须遵守单线程模型的原则:AndroidUI操作并不是线程安全的并且这些操作必须在UI线程中执行。在单线程模型中始终要记住两条法则:
1.不要阻塞UI线程
2.确保只在UI线程中访问AndroidUI工具包
当一个程序第一次启动时,Android会同时启动一个对应的主线程(MainThread),主线程主要负责处理与UI相关的事件,如:用户的按键事件,用户接触屏幕的事件以及屏幕绘图事件,并把相关的事件分发到对应的组件进行处理。所以主线程通常又被叫做UI线程。
比如说从网上获取一个网页,在一个TextView中将其源代码显示出来,这种涉及到网络操作的程序一般都是需要开一个线程完成网络访问,但是在获得页面源码后,是不能直接在网络操作线程中调TextView.setText()的因为其他线程中是不能直接访问主UI线程成员。
Android提供了几种在其他线程中访问UI线程的方法。
java代码:
Activity.runOnUiThread(Runnable)
View.post(Runnable)
View.postDelayed(Runnable,long)
Hanlder
这些类或方法同样会使你的代码很复杂很难理解。然而当你需要实现一些很复杂的操作并需要频繁地更新UI时这会变得更糟糕。
为了解决这个问题,Android1.5提供了一个工具类:AsyncTask,它使创建需要与用户界面交互的长时间运行的任务变得更简单。不需要借助线程和Handler即可实现。
AsyncTask是抽象类.AsyncTask定义了三种泛型类型Params,Progress和Result。
Params启动任务执行的输入参数,比如HTTP请求的URL。
Progress后台任务执行的百分比。
Result后台执行任务最终返回的结果,比如String。
AsyncTask的执行分为四个步骤,每一步都对应一个回调方法,这些方法不应该由应用程序调用,开发者需要做的就是实现这些方法。
1)子类化AsyncTask
2)实现AsyncTask中定义的下面一个或几个方法
onPreExecute(),该方法将在执行实际的后台操作前被UIthread调用。可以在该方法中做一些准备工作,如在界面上显示一个进度条。
doInBackground(Params...),将在onPreExecute方法执行后马上执行,该方法运行在后台线程中。这里将主要负责执行那些很耗时的后台计算工作。可以调用publishProgress方法来更新实时的任务进度。该方法是抽象方法,子类必须实现。
onProgressUpdate(Progress...),在publishProgress方法被调用后,UIthread将调用这个方法从而在界面上展示任务的进展情况,例如通过一个进度条进行展示。
onPostExecute(Result),在doInBackground执行完成后,onPostExecute方法将被UIthread调用,后台的计算结果将通过该方法传递到UIthread。
为了正确的使用AsyncTask类,以下是几条必须遵守的准则:
1)Task的实例必须在UIthread中创建
2)execute方法必须在UIthread中调用
3)不要手动的调用onPreExecute(),onPostExecute(Result),doInBackground(Params...),onProgressUpdate(Progress...)这几个方法
4)该task只能被执行一次,否则多次调用时将会出现异常
综合以下网址:
http://www.oschina.net/question/195301_31313
http://android.tgbus.com/Android/tutorial/201109/369193.shtml
1.线程的开销较大,如果每个任务都要创建一个线程,那么应用程序的效率要低很多;
2.线程无法管理,匿名线程创建并启动后就不受程序的控制了,如果有很多个请求发送,那么就会启动非常多的线程,系统将不堪重负;
3.另外,在新线程中更新UI还必须要引入handler,这让代码看上去非常臃肿;
为了解决这一问题,Android在1.5版本引入了AsyncTask.AsyncTask的特点是任务在主线程之外运行,而回调方法是在主线程中执行,这就有效地避免了使用Handler带来的麻烦。阅读AsyncTask的源码可知,AsyncTask是使用java.util.concurrent框架来管理线程以及任务的执行的,concurrent框架是一个非常成熟,高效的框架,经过了严格的测试。这说明AsyncTask的设计很好的解决了匿名线程存在的问题。
AsyncTask定义了三种泛型类型Params,Progress和Result.
Params启动任务执行的输入参数,比如HTTP请求的URL;
Progress后台任务执行的百分比;
Result后台执行任务最终返回的结果,比如String;
子类必须实现抽象方法doInBackground(Params…p),在此方法中实现任务的执行工作,比如连接网络获取数据等。通常还应该实现onPostExecute(Resultr)方法,因为应用程序关心的结果在此方法中返回。需要注意的是AsyncTask一定要在主线程中创建实例。
AsyncTask的执行分为四个步骤,每一步都对应一个回调方法,需要注意的是这些方法不应该由应用程序调用,开发者需要做的就是实现这些方法。在任务的执行过程中,这些方法被自动调用,运行过程,
onPreExecute()当任务执行之前开始调用此方法,可以在这里显示进度对话框。
doInBackground(Params…)此方法在后台线程执行,完成任务的主要工作,通常需要较长的时间。在执行过程中可以调用publicProgress(Progress…)来更新任务的进度。
onProgressUpdate(Progress…)此方法在主线程执行,用于显示任务执行的进度。
onPostExecute(Result)此方法在主线程执行,任务执行的结果作为此方法的参数返回。
01 | class GetImageTask extends AsyncTask<String,Void,Bitmap>{ |
02 | InputStreamis= null ; |
03 |
04 | @Override |
05 | protected BitmapdoInBackground(String...params){ |
06 | //TODOAuto-generatedmethodstub |
07 | URLmyFileUrl= null ; |
08 | Bitmapbitmap= null ; |
09 | InputStreamis= null ; |
10 | HttpURLConnectionconn= null ; |
11 | try { |
12 | myFileUrl= new URL(params[ 0 ]); |
13 | } catch (MalformedURLExceptione){ |
14 | e.printStackTrace(); |
15 | } |
16 | try { |
17 | conn=(HttpURLConnection)myFileUrl |
18 | .openConnection(); |
19 | conn.setDoInput( true ); |
20 | conn.connect(); |
21 | is=conn.getInputStream(); |
22 | bitmap=BitmapFactory.decodeStream(is); |
23 | is.close(); |
24 | } catch (IOExceptione){ |
25 | e.printStackTrace(); |
26 | } finally { |
27 | try { |
28 | if (is!= null ){ |
29 | is.close(); |
30 | } |
31 | if (conn!= null ){ |
32 | conn.disconnect(); |
33 | } |
34 | } catch (IOExceptione){ |
35 | //TODOAuto-generatedcatchblock |
36 | e.printStackTrace(); |
37 | } |
38 | } |
39 | return bitmap; |
40 | } |
41 |
42 | @Override |
43 | protected void onCancelled(){ |
44 | //TODOAuto-generatedmethodstub |
45 | super .onCancelled(); |
46 | } |
47 |
48 | @Override |
49 | protected void onPostExecute(Bitmapresult){ |
50 | //TODOAuto-generatedmethodstub |
51 | mImageAndTextView.setImage(result); |
52 | mImageAndTextView.postInvalidate( 0 , 0 ,mScreenWidth 30 ); //只更新稍比图片大一些的区域 |
53 | super .onPostExecute(result); |
54 | } |
55 |
56 | } |
1.不要阻塞UI线程
2.确保只在UI线程中访问AndroidUI工具包
当一个程序第一次启动时,Android会同时启动一个对应的主线程(MainThread),主线程主要负责处理与UI相关的事件,如:用户的按键事件,用户接触屏幕的事件以及屏幕绘图事件,并把相关的事件分发到对应的组件进行处理。所以主线程通常又被叫做UI线程。
比如说从网上获取一个网页,在一个TextView中将其源代码显示出来,这种涉及到网络操作的程序一般都是需要开一个线程完成网络访问,但是在获得页面源码后,是不能直接在网络操作线程中调TextView.setText()的因为其他线程中是不能直接访问主UI线程成员。
Android提供了几种在其他线程中访问UI线程的方法。
java代码:
Activity.runOnUiThread(Runnable)
View.post(Runnable)
View.postDelayed(Runnable,long)
Hanlder
这些类或方法同样会使你的代码很复杂很难理解。然而当你需要实现一些很复杂的操作并需要频繁地更新UI时这会变得更糟糕。
为了解决这个问题,Android1.5提供了一个工具类:AsyncTask,它使创建需要与用户界面交互的长时间运行的任务变得更简单。不需要借助线程和Handler即可实现。
AsyncTask是抽象类.AsyncTask定义了三种泛型类型Params,Progress和Result。
Params启动任务执行的输入参数,比如HTTP请求的URL。
Progress后台任务执行的百分比。
Result后台执行任务最终返回的结果,比如String。
AsyncTask的执行分为四个步骤,每一步都对应一个回调方法,这些方法不应该由应用程序调用,开发者需要做的就是实现这些方法。
1)子类化AsyncTask
2)实现AsyncTask中定义的下面一个或几个方法
onPreExecute(),该方法将在执行实际的后台操作前被UIthread调用。可以在该方法中做一些准备工作,如在界面上显示一个进度条。
doInBackground(Params...),将在onPreExecute方法执行后马上执行,该方法运行在后台线程中。这里将主要负责执行那些很耗时的后台计算工作。可以调用publishProgress方法来更新实时的任务进度。该方法是抽象方法,子类必须实现。
onProgressUpdate(Progress...),在publishProgress方法被调用后,UIthread将调用这个方法从而在界面上展示任务的进展情况,例如通过一个进度条进行展示。
onPostExecute(Result),在doInBackground执行完成后,onPostExecute方法将被UIthread调用,后台的计算结果将通过该方法传递到UIthread。
为了正确的使用AsyncTask类,以下是几条必须遵守的准则:
1)Task的实例必须在UIthread中创建
2)execute方法必须在UIthread中调用
3)不要手动的调用onPreExecute(),onPostExecute(Result),doInBackground(Params...),onProgressUpdate(Progress...)这几个方法
4)该task只能被执行一次,否则多次调用时将会出现异常
综合以下网址:
相关文章推荐
- Android使用AsyncTask下载图片并显示进度条功能
- Android 使用AsyncTask 下载图片的例子,学会使用AsyncTask
- Android 异步任务——AsyncTask (附使用AsyncTask下载图片Demo)
- Android使用AsyncTask下载图片,最好使用WeakReference
- 在android中使用AsyncTask从网络中下载图片,但是调用了execute方法后,最后不执行onPostExcute方法
- Android使用AsyncTask下载显示图片
- android-使用AsyncTask做下载进度条
- Android带进度条的下载图片示例(AsyncTask异步任务)
- Android异步下载网络图片&android解析xml文件的方式&使用Adapter为ListView提供数据
- Android使用webView长按保存下载网络图片
- Android中使用七牛云存储进行图片上传下载的实例代码
- android AsyncTask介绍 详解AsyncTask的使用 使用实例---加载网络图片
- Android图片下载框架Picasso 使用
- Android实现使用sftp下载linux服务器上的图片文件
- Android UI-开源框架ImageLoader完美使用+listview加载网络图片与下载
- Android之AsyncTask异步任务下载网络图片
- Android多线程分析之五:使用AsyncTask异步下载图像
- Java和Android Http连接程序:使用java.net.URL 下载服务器图片到客户端
- Android异步下载网络图片(其二:AsyncTask)
- Android中AsyncTask的简单用法及实现网络图片下载的实例