5

If I understand correctly the binary form of Java 10 is 100% identical to Java 9 so it shouldn't make any problems.

Is my assumption correct?

ZhekaKozlov
  • 36,558
  • 20
  • 126
  • 155
Mordechai
  • 15,437
  • 2
  • 41
  • 82
  • 1
    No, Java 10 class files are different – ZhekaKozlov Mar 20 '18 at 08:31
  • 5
    This has nothing to do with Java 10; the story for backward and forward compatibility hasn't changed. – Brian Goetz Mar 20 '18 at 14:42
  • @nullpointer God forbid, how is this a duplicate? I know that 8 added lambdas and wouldn't run on 7 without special flags. My question was if it runs w/o flags. – Mordechai Mar 20 '18 at 16:53
  • 2
    @Mordechai Its not about the byte code here. It never was(see the comment above). Plus, did you read the answer to another link in duplicate section? – Naman Mar 20 '18 at 16:55

2 Answers2

17

This has nothing to do with Java 10; the rules are the same as they've always been.

In every version of Java, the classfile version number has been incremented. You can run older classfiles on a newer Java runtime (you can run files compiled twenty years ago under Java 1.0 on Java 10!), but it has never been true that you can run newer classfiles on an older runtime. This hasn't changed with Java 10.

However, you can compile classes such that they run on older versions, if you don't use newer features introduced since that version. This used to be accomplished by the -source and -target switches:

// Run this on Java 8
javac -source 6 -target 6 Foo.java

and you'll get classfiles that will run on Java 6 and later. (The source version cannot be greater than the target version.) This was recently replaced with the more comprehensive --release option:

javac --release 9

which implies not only -source 9 and -target 9, but the compiler will also prevent you from using JDK functionality introduced after 9.

Brian Goetz
  • 90,105
  • 23
  • 150
  • 161
  • 2
    When using `--release 9`, why does `javac` version 10 prohibit the use of `var n = 1;`? I mean, it's only syntactic sugar, it's not as if it's something that affects the bytecode or the class file structure. – DodgyCodeException Mar 20 '18 at 17:02
  • 2
    @DodgyCodeException Because it's not part of the language as defined by the Java Language Specification for Java 9. There's no such concept as "Java 9, but with all the features from later versions that feel like syntactic sugar"; the language spec is versioned (8, 9, 10) and the `--source` option selects the language level according to the spec. – Brian Goetz Mar 20 '18 at 17:17
  • 1
    @DodgyCodeException And, even if it were a concept, users perceptions of what is "just syntactic sugar" are often deeply off. Everyone thought lambdas were "just syntactic sugar" for inner classes, but they are not (either semantically or in implementation.) – Brian Goetz Mar 20 '18 at 17:19
7

javac has supported a --release argument for a while. As long as you aren't using features from a newer release (in this case Java 10), you can do:

javac --release 9

And everything should work fine. Even better, the Java compiler will complain if there are issues that need to be addressed.

Note that without doing this you will get an UnsupportedClassVersionError even if the code is technically valid because the minimum Java version required is included in the compiled bytecode, and this defaults to the current version of the java compiler.

Nowadays you can also use multirelease jars if you want to use newer java language features but also include code supporting older JVMs.

avigil
  • 2,218
  • 11
  • 18