Java 是否有实际的理由来强制执行JDK版本的构建?

Java 是否有实际的理由来强制执行JDK版本的构建?,java,maven,gradle,Java,Maven,Gradle,存在可以强制生成只在特定JDK版本上运行的方法 我想知道有没有什么实际的理由可以这样做? 我们已经构建了用于指定源和目标版本的配置。据我所知,这已经足够了,因为Java是向后兼容的。例如,它在gradle中的外观: compileJava { sourceCompatibility = '1.8' targetCompatibility = '1.8' } maven就是这样的: <properties> <maven.compiler.source&

存在可以强制生成只在特定JDK版本上运行的方法

我想知道有没有什么实际的理由可以这样做? 我们已经构建了用于指定源和目标版本的配置。据我所知,这已经足够了,因为Java是向后兼容的。例如,它在gradle中的外观:

compileJava   {
  sourceCompatibility = '1.8'
  targetCompatibility = '1.8'
}
maven就是这样的:

  <properties>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
  </properties>

1.8
1.8
如果您看到任何需要确切jdk版本的原因,请您也写下来

UPD。 问题更多的是,编译版本8的java源/目标项目和JDK的版本8、9、10或11是否有任何实际区别…

一点也不。源代码主要是关于语法的。目标是关于特定的字节码幻数和功能

但您可以很好地编写符合Java7的代码,使用只有JDK8或更新版本提供的单个X类。然后,当您使用Java8JDK时,该编译器将找到该类X并构建良好。但是当在Java7JVM上运行该代码时,Java8类X丢失,导致运行时异常


因此:强制使用jdk会阻止您使用在目标版本之后添加到Java中的类

这样做的主要原因可能是在较新的JDK编译器中进行了一些更好的优化。因此,即使目标字节码级别与旧编译器相同,目标字节码本身也可能会得到改进

,这会增加它的重量:

有时,JVM的改进使得从源代码到字节码的更好转换成为可能。例如,在5之前,
Foo.class
被转换为反射调用;之后,向最不发达国家提供援助

因此,您可能有理由在整个组织中坚持使用给定的语言级别(因为共享代码),但特定的应用程序仍然可以利用VM的改进


编辑:对不起!引用的tweet是关于源代码低于目标代码的编译(例如
-source 8-target 11
),因此它与OP询问的内容不同。尽管如此,也许更新的编译器可以生成更好的字节码,即使目标保持不变



注:正如所建议的,让我提一下JDK 9+的使用,它阻止使用较新JDK的API,同时坚持使用较旧的语言级别。

原因有很多。我要指出的一点是在企业环境中部署

假设你在一家公司里有数千台维护的机器,你就不能在每台计算机上安装每一个java版本。此外,安全性通常不允许下载(通常根本不允许直接访问互联网),而且每一个可用的Java版本都需要维护安全性,需要进行大量的书面工作和讨论(例如安全性)

Botomline是:在企业中,可用的Java版本非常有限,通常不是最前沿的

现在,假设可用的版本是Java8。现在,如果您希望应用程序在环境中运行,您必须确保它在可用版本(如Java8)上实际运行。如果它将使用该版本中不可用的东西,它将不会运行或崩溃。本质上,这样的应用程序在企业中根本不可用。这意味着企业将寻找一种不同的解决方案,他们可以在自己的环境中实际使用


因此,能够告诉编译器目标版本有助于创建一个能够并且将实际使用的应用程序(并且不会在用户机器上崩溃)

例如,我不能用JDK 7编译JDK 8流。我的问题不是用旧版本编译新代码,而是用最新的JDK编译旧代码。关于这个答案,值得一提的是JDK 9+的,这会阻止使用较新JDK的API。@TomaszLinkowski我建议在回答中包含此
--release
标志信息。