Java 8默认方法会破坏源代码兼容性吗?
Java 8默认方法会破坏源代码兼容性吗?
Java源代码通常是向前兼容的。在Java 8之前,据我所知,编译后的类和源代码都与后续的JDK/JVM版本兼容。然而,随着Java 8中默认方法的添加,这似乎不再适用。
例如,我使用的一个库中有一个实现了java.util.List
的实现,其中包括一个List
方法。这个方法返回一个经过排序的列表的副本。这个库作为一个jar文件依赖项部署,可以在使用JDK 1.8构建的项目中正常工作。
然而,后来我有机会使用JDK 1.8重新编译库本身,我发现该库不再编译:具有自己的sort()
方法的List
实现类现在与Java 8中的java.util.List.sort()
默认方法发生冲突。Java 8的sort()
默认方法在原地对列表进行排序(返回void
);我的库的sort()
方法 - 因为它返回一个新的排序列表 - 具有不兼容的签名。
所以我的基本问题是:
- JDK 1.8是否引入了由于默认方法而导致的Java源代码的向前不兼容性?
还有:
- 这是第一个这样的向前不兼容的变化吗?
- 在设计和实现默认方法时是否考虑或讨论过这个问题?有没有文档记录?
- 与好处相比,这个(尽管很小的)不便被忽视了吗?
以下是一些在1.7下编译和运行,在1.8下运行但在1.8下无法编译的代码示例:
import java.util.*; public final class Sort8 { public static void main(String[] args) { SortableListl = new SortableList (Arrays.asList(args)); System.out.println("unsorted: "+l); SortableList s = l.sort(Collections.reverseOrder()); System.out.println("sorted : "+s); } public static class SortableList extends ArrayList { public SortableList() { super(); } public SortableList(Collection extends V> col) { super(col); } public SortableList sort(Comparator super V> cmp) { SortableList l = new SortableList (); l.addAll(this); Collections.sort(l, cmp); return l; } } }
以下显示了这段代码的编译情况(或失败情况)和运行情况。
> c:\tools\jdk1.7.0_10\bin\javac Sort8.java > c:\tools\jdk1.7.0_10\bin\java Sort8 this is a test unsorted: [this, is, a, test] sorted : [this, test, is, a] > c:\tools\jdk1.8.0_05\bin\java Sort8 this is a test unsorted: [this, is, a, test] sorted : [this, test, is, a] > del Sort8*.class > c:\tools\jdk1.8.0_05\bin\javac Sort8.java Sort8.java:46: error: sort(Comparator super V>) in SortableList cannot implement sort(Comparator super E>) in List public SortableListsort(Comparator super V> cmp) { ^ return type SortableList is not compatible with void where V,E are type-variables: V extends Object declared in class SortableList E extends Object declared in interface List 1 error