欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Android異步回調(diào)中的UI同步性問題分析

 更新時(shí)間:2016年06月01日 16:27:11   作者:Windstep  
這篇文章主要為大家詳細(xì)分析了Android異步回調(diào)中的UI同步性問題,感興趣的小伙伴們可以參考一下

Android程序編碼過程中,回調(diào)無處不在。從最常見的Activity生命周期回調(diào)開始,到BroadcastReceiver、Service以及Sqlite等。Activity、BroadcastReceiver和Service這些基本組件的回調(diào)路徑和過程也就是通常意義上所謂的“生命周期”。同時(shí),在處理具體的業(yè)務(wù)邏輯時(shí),常常設(shè)計(jì)到不同線程之間的通信,如下載圖片完成后通知 UI線程更新UI,凡此類場景,無論使用哪一種具體的線程間通信方式(Handler/Message、Handler/post、基于接口的回調(diào)、基于多對多的觀察者模式如EventBus等),其本質(zhì)上都是基于“回調(diào)”。在實(shí)際編碼過程中,凡涉及到不同線程之間的通信,本質(zhì)上更是屬于“異步回調(diào)”。當(dāng)需要在“異步回調(diào)”中修改UI時(shí),此時(shí)需要特別注意UI同步性問題。

為了便于問題的闡述,在此先對“Android異步回調(diào)UI同步性問題”進(jìn)行如下界定:當(dāng)異步回調(diào)執(zhí)行時(shí)(稱之為“異步回調(diào)執(zhí)行點(diǎn)”),當(dāng)前UI界面上的元素與最初生成此異步回調(diào)的調(diào)用器開始執(zhí)行時(shí)(稱之為“異步回調(diào)生成點(diǎn)”)的UI元素已經(jīng)存在不一致,不一致不僅包括UI元素可能的界面變化、可能的內(nèi)容變化,也包括“異步回調(diào)執(zhí)行點(diǎn)”和“異步回調(diào)生成點(diǎn)”時(shí)的UI元素中的某一特性的表征量(如某一具有表征當(dāng)前UI元素的字段值)相關(guān),即使UI元素界面和內(nèi)容都尚未發(fā)生變化。

編碼過程中,“Android異步回調(diào)UI同步性問題”經(jīng)常存在,有時(shí)候稍不注意會產(chǎn)生一些看起來難以理解的bug,并由于異步特性的存在,此類bug還具有一定的隨機(jī)性。有時(shí)候由于一些需求的復(fù)雜性,此類bug隱蔽性很強(qiáng),也容易被忽略。至少到目前為止,在實(shí)際開發(fā)中,本人遇到此類問題已有數(shù)個。

純文字的描述可能不太好理解,下面以一個很常用的Android-Universal-Image-Loader為例,簡單舉例一個潛在存在的“Android異步回調(diào)UI同步性問題”。

ListView Item View中有ImageView,通過Android-Universal-Image-Loader去加載顯示,圖片加載完成后需要做一些邏輯處理(如隱藏圖片加載進(jìn)度條等..),通常代碼如下:

ImageLoader.getInstance().loadImage(imageUrl, new ImageLoadingListener() {
        
 @Override
 public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
  if (loadedImage != null) {
   imageView.setImageBitmap(loadedImage);
   // 其他業(yè)務(wù)邏輯處理..
  }
 }

 @Override
 public void onLoadingStarted(String imageUri, View view) {
  
 }

 @Override
 public void onLoadingCancelled(String arg0, View arg1) {
  
 }

 @Override
 public void onLoadingFailed(String arg0, View arg1, FailReason arg2) {
  
 }
});

初看上去,代碼邏輯好像也沒什么問題,網(wǎng)上大部分人也是這么寫的。當(dāng)較慢滑動ListView時(shí),或在平時(shí)正常使用時(shí),也沒有什么問題。但是此處的代碼邏輯真的嚴(yán)密嗎?

ListView的getView復(fù)用特性,大家也都熟知。對于之前遇到的“圖片錯位/先顯示之前的圖片后再被正確的圖片覆蓋掉”,此類現(xiàn)象也都知道如何解決(在getView邏輯開始處理處將ImageView設(shè)置成最先的默認(rèn)圖片,其他UI元素類似處理),基本上也不會再有“圖片錯位/先顯示之前的圖片后再被正確的圖片覆蓋掉”這類現(xiàn)象了。實(shí)際上,當(dāng)網(wǎng)速條件一般,且loadImage大致與上述代碼所示,在ListView中快速滑動列表,幾屏后,不出意外,會發(fā)現(xiàn)“圖片錯位/先顯示之前的圖片后再被正確的圖片覆蓋掉”此問題依然存在。

此時(shí)問題出現(xiàn)的原因不在于getView本身,因?yàn)間etView邏輯開始時(shí)已經(jīng)將ImageView重置為默認(rèn)圖片,而在于“Android異步回調(diào)UI同步性問題”。由于ViewHolder的不斷復(fù)用,網(wǎng)速一般時(shí)快速滑動幾屏后,onLoadingComplete的異步回調(diào)執(zhí)行時(shí)與當(dāng)前UI元素已經(jīng)存在不一致,簡單點(diǎn)理解,ImageView被復(fù)用了ImageView position 0,ImageView position 11, ImageView position 21,此時(shí)滑動停止,onLoadingComplete的異步回調(diào)執(zhí)行時(shí)ImageView已經(jīng)是最后一次的ImageView position 21,而onLoadingComplete的異步回調(diào)可能被執(zhí)行數(shù)次(ImageView position 0,ImageView position 11, ImageView position 21,且順序還取決于異步中的具體處理和網(wǎng)絡(luò)環(huán)境等),于是問題發(fā)生了。

解決方案:
抓住”UI元素中的某一特性的表征量“,在異步回調(diào)中通過比較“異步回調(diào)生成點(diǎn)”和“異步回調(diào)執(zhí)行點(diǎn)”此特征變量的值直接作出邏輯上的處理。

public class HardRefSimpleImageLoadingListener implements ImageLoadingListener {

 public int identifier;

 public HardRefSimpleImageLoadingListener() {
 }

 public HardRefSimpleImageLoadingListener(int identifier) {
  this.identifier = identifier;
 }

 @Override
 public void onLoadingCancelled(String arg0, View arg1) {

 }

 @Override
 public void onLoadingComplete(String arg0, View arg1, Bitmap arg2) {

 }

 @Override
 public void onLoadingFailed(String arg0, View arg1, FailReason arg2) {

 }

 @Override
 public void onLoadingStarted(String arg0, View view) {
 
 }
}

ImageLoader.getInstance().loadImage(imageUrl, new HardRefSimpleImageLoadingListener(did) {
 @Override
 public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {
  if (loadedImage != null) {
   if (identifier != did) {
    return;
   }
   imageView.setImageBitmap(loadedImage);
   // 其他業(yè)務(wù)邏輯處理..
  }
 }
});


總之,凡此類“Android異步回調(diào)UI同步性問題”,最好都通過比較“異步回調(diào)生成點(diǎn)”“異步回調(diào)執(zhí)行點(diǎn)”特征變量的值去針對性的做邏輯處理,以免出現(xiàn)不必要的Bug,是非常必要且有效的手段。

 原文地址:http://www.cnblogs.com/lwbqqyumidi/p/4110377.html

以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • Android自定義View實(shí)現(xiàn)支付寶咻一咻效果

    Android自定義View實(shí)現(xiàn)支付寶咻一咻效果

    這篇文章主要為大家詳細(xì)介紹了Android自定義View實(shí)現(xiàn)支付寶咻一咻效果的相關(guān)資料,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-02-02
  • Android實(shí)現(xiàn)微信分享帶有縮略圖的網(wǎng)頁

    Android實(shí)現(xiàn)微信分享帶有縮略圖的網(wǎng)頁

    最近做了一個web app的項(xiàng)目,要求分享web頁還要帶有圖片功能,怎么實(shí)現(xiàn)呢?今天小編給大家分享android實(shí)現(xiàn)微信分享帶有縮略圖的網(wǎng)頁功能,需要的朋友參考下
    2017-02-02
  • flutter PositionedTransition實(shí)現(xiàn)縮放動畫

    flutter PositionedTransition實(shí)現(xiàn)縮放動畫

    這篇文章主要為大家詳細(xì)介紹了flutter PositionedTransition實(shí)現(xiàn)縮放動畫,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2019-07-07
  • Android開發(fā)方式之Java+html+javascript混合開發(fā)

    Android開發(fā)方式之Java+html+javascript混合開發(fā)

    這篇文章主要為大家詳細(xì)介紹了Android開發(fā)方式的其中一種Java+html+javascript混合開發(fā),感興趣的小伙伴們可以參考一下
    2016-06-06
  • 基于RxJava框架實(shí)現(xiàn)獲取驗(yàn)證碼的輔助類

    基于RxJava框架實(shí)現(xiàn)獲取驗(yàn)證碼的輔助類

    這篇文章主要為大家詳細(xì)介紹了基于RxJava框架實(shí)現(xiàn)獲取驗(yàn)證碼的輔助類,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-06-06
  • Android仿京東、天貓下拉刷新效果

    Android仿京東、天貓下拉刷新效果

    這篇文章主要為大家詳細(xì)介紹了Android仿京東、天貓下拉刷新效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-03-03
  • Android自定義引導(dǎo)玩轉(zhuǎn)ViewPager的方法詳解

    Android自定義引導(dǎo)玩轉(zhuǎn)ViewPager的方法詳解

    這篇文章主要給大家介紹了關(guān)于Android自定義引導(dǎo)玩轉(zhuǎn)ViewPager的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對各位Android開發(fā)者們具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-06-06
  • Intent傳遞對象之Serializable和Parcelable的區(qū)別

    Intent傳遞對象之Serializable和Parcelable的區(qū)別

    Intent在不同的組件中傳遞對象數(shù)據(jù)的應(yīng)用非常普遍,大家都知道在intent傳遞對象的方法有兩種:1、實(shí)現(xiàn)Serializable接口、2、實(shí)現(xiàn)Parcelable接口,接下來通過本文給大家介紹Intent傳遞對象之Serializable和Parcelable的區(qū)別,感興趣的朋友一起學(xué)習(xí)吧
    2016-01-01
  • Android崩潰日志收集和保存解析

    Android崩潰日志收集和保存解析

    這篇文章主要為大家介紹了Android崩潰日志收集和保存解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-02-02
  • Android 多渠道打包進(jìn)階版

    Android 多渠道打包進(jìn)階版

    上篇文章更了Android 多渠道打包,這篇文章將做一個后續(xù)繼續(xù)更Android 多渠道打包進(jìn)階版,上次意未盡的朋友可以繼續(xù)啦,第一次點(diǎn)進(jìn)來的朋友也可以看上次文章
    2021-09-09

最新評論