Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Casting a primitive vs Creating a object of the primitive

Tags:

java

I'm not habitual to casting a primitive data type to an object. Saw some code like:

public static int CompareAges(Person p1, Person p2) {
    Integer age1 = p1.getAge();
    return age1.compareTo(p2.getAge());
}

The instantiation of age1 seemed extraneous, so I tried to write the code as:

public static int CompareAges(Person p1, Person p2) {
    return p1.getAge().compareTo(p2.getAge());
}

But that raised a compiler error because p1.getAge() is a primitive data type int and not an Integer, which is an object.

Intuitively, I did:

public static int CompareAges(Person p1, Person p2) {
    return ((Integer) p1.getAge()).compareTo(p2.getAge());
}

and it worked!

The question: What did I miss? Since when did we start casting primitives as value types?

like image 355
displayName Avatar asked Mar 13 '16 22:03

displayName


People also ask

What is primitive casting?

Casting between primitive types enables you to convert the value of one type to another primitive type. This most commonly occurs with the numeric types. But one primitive type can never be used in a cast. Boolean values must be either true or false and cannot be used in a casting operation.

What is the difference between a primitive and an object?

Primitive values are immutable — they cannot be changed after being created. Object references, however, are mutable and can be changed. Since objects are stored as references, special care must be taken when duplicating objects and when performing equality checks on objects.

What is the difference between primitive and wrapper?

One major difference from the explanation above is, default values of the primitive types depend on type like int is 0, char is \u0000, boolean is false, etc but the default value for wrapper classes of all types is null since they are objects.

Why is it sometimes necessary to cast an object to another type in our code?

Casting a variable to a data type basically is telling the compiler "Trust me, I know what I'm doing." In the case of casting an "Object" to "Book", you are assuring the compiler that the object is, in fact, a Book and to proceed accordingly. It also as the effect of forcing you to believe you know what you are doing.


2 Answers

It's what happens internally:

1. Integer age1 = p1.getAge();
       Integer != int
       Integer = Integer.valueOf(int)
   Integer age1 = Integer.valueOf(p1.getAge());

2. p1.getAge().compareTo(p2.getAge());
       int.compareTo(int)
       ^^^
       // it's just a primitive type, as a result - the compile error

3. ((Integer) p1.getAge()).compareTo(p2.getAge())
       Integer.compareTo(int)
       Integer.compareTo(Integer.valueOf(int))
   ((Integer) p1.getAge()).compareTo(Integer.valueOf(p2.getAge()))

4. (Integer) p1.getAge() ---> Integer.valueOf(p1.getAge()) 
       // why so? look at callOfCode's answer

But, in my opinion, ((Integer) p1.getAge()).compareTo(p2.getAge()) looks ugly.

I would replace it to

p1.getAge() > p2.getAge() ? 1 : (p1.getAge() < p2.getAge() ? -1 : 0)

or to

Integer.compare(p1.getAge(), p2.getAge()) // java 7+

I wouldn't like to do casting in this case.


More about "autoboxing/unboxing" you may find here.

like image 191
Andrew Tobilko Avatar answered Sep 25 '22 07:09

Andrew Tobilko


Each primitive has its own boxing type

enter image description here

The Boxing could be implicit (Autoboxing) or explicit like you did it in your code.

p2.getAge() is an Example of AutoBoxing or Implicit Boxing. The method compareTo takes an Object. As it is a primitive, Java converts it automatically to the correspondent Boxing Object (Integer). You did the explicit Boxing with the cast (Integer) p1.getAge()

like image 42
Yassin Hajaj Avatar answered Sep 23 '22 07:09

Yassin Hajaj