Dynamic typing inside the Java Virtual Machine

Take a look at the following Java program. Albeit it’s dynamic typing style, it’s accepted by the Java compiler javac:

public class Dynamic {
  public static void main(String[] args) {
	Object o;
	o = System.out;
	o = System.in;
	o = 1;
	o = "Hello World";

The method body part of the compiled JVM code looks something like this:

   0:   getstatic       #2; //Field java/lang/System.out:Ljava/io/PrintStream;
   3:   astore_1
   4:   getstatic       #3; //Field java/lang/System.in:Ljava/io/InputStream;
   7:   astore_1
   8:   iconst_1
   9:   invokestatic    #4; //Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
   12:  astore_1
   13:  ldc     #5; //String Hello World
   15:  astore_1

At line 0, 4, 8, 9 and 13 something is pushed on the operand stack. Line 3, 7, 12 and 15 pop the top record from the operand stack and assign it to local variable #1. Line 8-9 is called boxing. Since o is a java.lang.Object and Java doesn’t allow java.lang.Object to take a primitive value, like the int 1, this value is boxed in a java.lang.Integer object at line 9. The Java compiler javac created line 9 because Java is based on static typing.

Dynamic typing means that values have types but variables don’t. In static typing, variables have types and are restricted to not refer to any random type of value. The local variable o has type java.lang.Object and can only refer to values of type java.lang.Object or its subtypes.

Unlike Java, local JVM variables are dynamically typed — NOT statically typed. We can safely remove line 9 (the conversion from int to java.lang.Integer) from the JVM code and it will still be perfectly valid JVM code. Local variable #1 will then in turn be assigned a PrintStream, an InputStream, an int and a String. This is possible because local variable #1 – like all local variables in the JVM – has no type.


%d bloggers like this: