为什么Java 8 Streams只在API级别24及以上可用?

7
支持的Java 8语言特性和API中指出,我们可以在任何最低sdk API级别的android项目中使用默认方法和lambda表达式。

然而,Stream库(java.util.stream)仅支持API 24及更高版本。有人能否解释一下为什么会这样?在我看来,这并不合理,因为据我所知,流API的添加不需要JVM修改,就像添加lambda或默认方法一样;它只是利用Java 8特性,例如集合上的默认方法,并向Java工具库添加了一些新代码。


可能在流中有更多的类型推断吗? - OldCurmudgeon
5
“much more type inferencing”意思是更多的类型推断,但并不是那么多(就像streamsupport这样的后移植工具所展示的那样)。我相信主要的技术难题之一是,事后将java.util Collection API改造成可进行类型推断是不可行的。 - Sartorius
5
正好相反,因为lambda表达式等被展开,它们不需要特殊的执行环境,正如您所链接页面上的表格显示的那样(请注意右侧的“任意”)。相比之下,新的API需要一个新的API版本。 - Holger
2
@Holger 所以基本上问题只是更新运行 < 24 的设备的核心库,并且不需要修改 ART 来使用流 API? - AAryz
4
我会尽力为您翻译。以下是翻译的结果:@AAryz 更新设备使用新的核心库。据我所知,基本上是这样。已经有第三方利用了Android Studio 3.x中lambda解糖的方式。唯一缺少的是核心运行时中更新后的java.util Collection API。从技术上讲,虽然可能性存在,但当然不切实际。 - Sartorius
4
是的,新的或替代性库可以解决这个问题。原则上,也可以通过字节码插装来将所有新API用法重定向到您随应用程序一起提供的第三方库。或者您可以使用像Sartorius一开始链接的第三方库。 - Holger
2个回答

6

能否有人解释一下为什么会出现这种情况?

因为谷歌没有时间机器。或者说,如果有的话,他们并没有用它来“修改”之前的 Android 版本。

就是它简单地利用了 Java 8 特性(如集合中的默认方法),并在 java util 库中添加了一些新代码吗?

没错。然而,谷歌无法更改之前 Android 版本上的 java.util 类。即使通过库添加新的 java.util 类也会存在问题。


1
这是因为java.util包是Android.jar的一部分,即用户手机上的Android框架类(如Activity),并不会与每个应用程序分开携带。
这就是为什么现在Android将几乎所有功能作为Android X库的一部分添加,以便支持所有Android版本。
但是,使用Android Gradle插件4.0+,您也可以在旧的API级别中使用流API。
您需要添加desugaring库。
dependencies{
  coreLibraryDesugaring 'com.android.tools:desugar_jdk_libs:1.0.9'
}

并且在compileOptions中添加coreLibraryDesugaringEnabled标志:

compileOptions {
    // Flag to enable support for the new language APIs
    coreLibraryDesugaringEnabled true
    // Sets Java compatibility to Java 8
    sourceCompatibility JavaVersion.VERSION_1_8
    targetCompatibility JavaVersion.VERSION_1_8
  }

这将确保在应用程序中的 API 版本小于 24 的情况下,新的 Java lang API 将通过该库添加。
来源:https://developer.android.com/studio/write/java8-support#library-desugaring

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接