Android SparseArray

在Android中提供了一组SparseArray类,用来存储key为整数时的key-value值。Android提供的SparseArray类有SparseArray, LongSparseArray, SparseBooleanArray, SparseIntArray和SparseLongArray五种类型。其中SparseArray用来存储key为Integer,value为任意类型的key-value值,LongSparseArray用来存储key为Long,value为任意类型的key-value值,SparseBooleanArray, SparseIntArray和SparseLongArray则分别用来存储key为Integer,value为Boolean,Integer和Long类型的key-value值。
在Eclipse中使用HashMap< Integer, T >定义变量时总是会提示”Use new SparseArray< T >(…) instead for better performance”(在Android Studio中似乎没有看到此提示),也就是说ADT建议使用SparseArray替代HashMap< Integer, T >,以提供更好的性能。当使用其他几种特定key-value类型的HashMap时也会有类似的提示。为了性能考虑,还是采纳ADT的建议,使用SparseArray来代替HashMap。

SparseArray.clone()方法异常

SparseArray系列类提供了一系列用来添加,删除,获取Array元素的方法。其中有一个clone()方法,可以用来生成一个SparseArray对象的拷贝。但是当我们通过试图如下代码去拷贝一个SparseArray对象时
,会发现在部分系统中会抛出java.lang.NoSuchMethodError异常。

SparseArray<String> anotherArray = srcArray.clone();

这里写图片描述

问题原因

查看Android API Level 14(Android 4.0)版本的 api变化(http://developer.android.com/sdk/api_diff/14/changes/),可以看到SparseArray的clone()方法是Android4.0版本中才开始有的,在Android4.0以下的版本中并没有此方法。所以在Android4.0以下的版本中执行SparseArray.clone()就会抛出此异常。
在Android中新的SDK版本中添加新的类和方法是很常见的。在AndroidManifest.xml中会指定minSdkVersion版本,也就是应用需要支持的最低SDK版本。为了避免产生这类在低版本系统中执行高版本才有的api导致的异常,在开发时Android Lint会自动检查在代码中是否使用了高于minSdkVersion版本中的api,如果在项目代码中使用了高于minSdkVersion版本中才有的新的api,会给出一个call new api的Lint Error。
然而不幸的是,google将SparseArray的clone()方法错误的标记为从api level 1就开始支持的api。这导致Android Lint无法检查出SparseArray的clone()方法的调用问题,开发者也无从知道这个api调用会导致的潜在异常。
这里写图片描述
这个问题在Eclipse+ADT和Android Studio中都存在。
此外,由于此处抛出的是NoSuchMethodError,不是NoSuchMethodException,不能通过catch(Exception)来捕获。如果需要捕获此错误,需要用catch(Error),例如

try { anotherArray = srcArray.clone(); } catch (NoSuchMethodError e) { e.printStackTrace(); }

解决方法

代码中增加判断,如果是Android4.0以下版本,通过遍历方式来实现对象拷贝。例如:

SparseArray<String> anotherArray;if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {    anotherArray = srcArray.clone();} else {    anotherArray = new SparseArray<>();    for (int i = 0; i < srcArray.size(); i++) {        int key = srcArray.keyAt(i);        String value = srcArray.valueAt(i);        anotherArray.append(key, value);    }}

参考:https://code.google.com/p/android/issues/detail?id=39242

更多相关文章

  1. Android Studio:xxx is not an enclosing class 错误的解决方法
  2. 【Android】Android 发送短信和打电话的方法
  3. Android中AutoCompleteTextView的特殊使用方法
  4. Android 解决fragment replace方法低效的问题
  5. android 修改系统各种类型的声音的默认值和最大最小值
  6. Android中WARNING: Application does not specify an API level
  7. Android开发SDK版本号和API level对照表,到Android 10.0
  8. 使用android中的handler延迟执行方法

随机推荐

  1. Android(安卓)中startActivity 与startAc
  2. android 国际化
  3. Some Android licenses not accepted. To
  4. Ubuntu搭建android编译环境总结
  5. Android 使用腾讯TBS遇到的坑
  6. android练习一之走马灯效果
  7. android——写xml
  8. Android 实现两屏幕互相滑动
  9. 学习Android camera笔记 & 调用流程
  10. 通过UserAgent判断智能手机(设备,Android