I decompiled Java 10's local variable type inference

I decompiled Java 10's local variable type inference

Click "Hollis" above to follow me, and the exciting content will be presented immediately.
Full text: 2500
Reading time: 5 minutes
Beijing time on March 21, Oracle officially announced the official release of Java 10. This is the first official release after the major version cycle of Java. Regarding Java 10, one of the new features worthy of programmers’ attention is probably local-variable type inference.

After the launch of Java 10, many articles have also come out, telling us what features are there, and how to use local variable type inference. However, to know why, we must know why.

After the release of Java 10, I downloaded this version of Jdk and installed it on my computer for the first time, then wrote a piece of code, and tried to decompile it, and really feel how local variable inference is. This article briefly talks about my feelings.

principle


Regarding the usage of local variable type inference, I have introduced it in my "Java 10 will be released this month, it will change the way you write code". It can be used in the following scenarios:

public class VarDemo {

   public static void main(String[] args) {
       //初始化局部变量  
       var string = "hollis";
       //初始化局部变量  
       var stringList = new ArrayList<String>();
       stringList.add("hollis");
       stringList.add("chuang");
       stringList.add("weChat:hollis");
       stringList.add("blog:http://www.hollischuang.com");
       //增强for循环的索引
       for (var s : stringList){
           System.out.println(s);
       }
       //传统for循环的局部变量定义
       for (var i = 0; i < stringList.size(); i++){
           System.out.println(stringList.get(i));
       }
   }
}

Then, use the javac command of java 10 to compile:

/Library/Java/JavaVirtualMachines/jdk-10.jdk/Contents/Home/bin/javac VarDemo.java

Generate VarDemo.class file, we decompile VarDemo.class. Decompile with jad to get the following code:


public class VarDemo
{
   public static void main(String args[])
   {
       String s = "hollis";
       ArrayList arraylist = new ArrayList();
       arraylist.add("hollis");
       arraylist.add("chuang");
       arraylist.add("weChat:hollis");
       arraylist.add("blog:http://www.hollischuang.com");
       String s1;
       for(Iterator iterator = arraylist.iterator(); iterator.hasNext(); System.out.println(s1))
           s1 = (String)iterator.next();

       for(int i = 0; i < arraylist.size(); i++)
           System.out.println((String)arraylist.get(i));

   }
}

This code is very familiar to us. It is the code written before Java 10 when there is no local variable type inference. The corresponding relationship of the code is as follows:

本地变量类型推断写法  正常写法
var string = "hollis";  String string = "hollis";
var stringList = new ArrayList();   ArrayList stringList = new ArrayList();
for (var s : stringList)    for (String s : stringList)
for (var i = 0; i < stringList.size(); i++) for (int i = 0; i < stringList.size(); i++)
ArrayList arraylist = new ArrayList(); 其实是
ArrayList<String> stringList = new ArrayList<String>();解糖后,类型擦除后的写法。

for(Iterator iterator = arraylist.iterator(); iterator.hasNext(); System.out.println(s1)) 其实是 for (String s : stringList) 这种for循环解糖后的写法。

Therefore, local variable type inference is also syntactic sugar provided to developers by Java 10. Although we use var in the code to define, but for the virtual machine, he does not recognize this var. In the process of compiling the java file into a class file, it will solve the sugar and use the real type of the variable to replace the var ( Such as using String string to replace var string). For the virtual machine, there is no need to make any compatibility changes to var, because its life cycle ends in the compilation phase. The only change is that the compiler needs to add an extra sugar-resolving operation on var during the compilation process.

Interested students can write two pieces of code, one with var and one without var, and then compare the compiled bytecode. You will find that it is really exactly the same. The figure below is the result of my comparison with the diff tool.
I decompiled Java 10's local variable type inference


语法糖(Syntactic Sugar),也称糖衣语法,是由英国计算机学家 Peter.J.Landin 发明的一个术语,指在计算机语言中添加的某种语法,这种语法对语言的功能并没有影响,但是更方便程序员使用。简而言之,语法糖让程序更加简洁,有更高的可读性。

What is the difference with JavaScript


Many people know that in JavaScript, the definition of variables is declared using var. So, as soon as Java 10's local variable type inference came out, some people said, isn't this copying JavaScript? Isn't this the same as var in JS?

Actually, it's really different.

First of all, JavaScript is a weakly typed (or dynamically typed) language, that is, the type of variable is uncertain. You can use the syntax "5"-4 in JavaScript, and its result is the number 1, where the string and the number are calculated. If you don’t believe it, you open the console of your browser and try it:
I decompiled Java 10's local variable type inference

However, although var can be used to declare variables in Java, it is still a strongly typed language. Through the decompiled code above, we already know that var is just a syntactic sugar provided by Java to developers. Finally, after compilation, the object type defined by var must be defined as the type inferred by the compiler.

Will it affect readability?


Local variable type inference is probably the most criticized for its readability, because before, when we define a variable, we must clearly specify its type, so when you read the code, you can know its type by looking at its declared type. , But after all use var, it will be miserable. There is no doubt that this will lose part of the readability. However, using var to declare objects in the code also brings many benefits, such as more concise code.

Before a new thing comes out, there will always be all kinds of uneasiness. Now everyone feels that this thing too affects my efficiency in reading code. Just like when Taobao Mall just changed its name to Tmall, everyone thought it was a ghost name. I'm used to listening now, don't you think it's pretty good?

If everyone uses var to declare variables, then the name of the variable becomes more important. At that time, everyone will pay more attention to the readability of variable names. Moreover, I believe that in the near future, major IDEs will launch the inferred type function of smart display variables. Therefore, from all aspects, some shortcomings can be made up.

In short, I am more actively embracing the feature of local variable type inference.

Thinking


Finally, I would like to ask one more question for everyone to think about. Local variable type inference seems to be quite easy to use, and since Java has decided to release it in the new version, why should it limit its usage? The few known scenarios where var can be used to declare variables are to initialize local variables, enhance the index of the for loop, and define the local variables of the traditional for loop. There are also several scenarios that do not support this usage, such as:
method parameters
parameter constructor
return type of method
member variable objects
so my question is, why do these restrictions Java, what consideration is that? Reliable students are rewarded. Pull you into my knowledge planet for free. Discussions and answers on this part of the thinking questions will also be conducted on Knowledge Planet.

-MORE | More exciting articles-

  • Java engineer's road to becoming a god (2018 revision)
  • 8 website*** technologies that Java development must master
  • The most thorough article on the whole network to analyze the hash() in Map
  • Large-scale website architecture technology at a glance

If you see this, you like this article.

Then please press and hold the QR code to follow Hollis

I decompiled Java 10's local variable type inference

Guess you like

Origin blog.51cto.com/13626762/2545042