Double wrapper initialization with int does not compile

Asked

Viewed 159 times

3

I want to understand why this boot doesn’t work:

(1): Double d = 10; // Não funciona

I understand that Double is a wrapper, the compiler should convert this line to:

(2): Double d = Double.valueOf(10); // Funciona

But it seems that’s not quite it because (1) is not compiling, if I do (2) explicitly compiles.

What is the justification for this?

  • This answer responds directly and summarized what occurred there.

  • @Diegof there occurred something a little different

2 answers

3


With the comments it is clear that there is a confusion between Boxing and casting. They are completely different concepts.

Boxing

What the guy Double makes is the Boxing of floating point values with double precision. It does not convert, does not promote anything. It takes this value and places it within a class called Double.

This class is a type by reference, so the variable that will contain the value has a pointer to the object where the data is. The stored value is there in the object and can only be accessed indirectly through the pointer. The compiler already does this by the programmer.

This is what is called boxing a value into an object. There is nothing conversion here.

Casting

Casting is a process of promoting from one type to another. In some cases it is only to indicate to the compiler that the value should be interpreted as if it were another. In another it is necessary to do a conversion, since its internal structure is different. When it is possible to do it safely the compiler applies the casting automatically in some situations preestablished by language.

I talked about it in What is upcasting and downcasting in the Java language?.

This is because there are rules in the language of self-promotion of compatible types only among the primitive types of language*. Works:

double d1 = 10;

double is a "primitive type". Double it is not, this is already known. So in class use there is no promotion of an entire number for the Double. There is no rule that determines what must be done.

They could have defined it in the language, but they did not and it makes sense not to do it in the language itself. If they had, I could have had a cast implicit in the class Double. This, of course, if Java allowed the definition of operators in the classes.

It is possible to make a cast explicit, then everything ok:

Double d2 = (double)10;

It is possible to pass a value that is already a double through literals:

Double d3 = 10.0;
Double d4 = 10d;

Or through a constructor or another method (used in the question) that creates a double-precision number:

Double d5 = new Double(10);

Note that the builder expects a double and the whole promotion to this type occurs implicitly as per the language specification.

Behold working in the ideone. And in the repl it.. Also put on the Github for future reference.

The Boxing for Double expects a number of the type double to box it, if it doesn’t get exactly this, it doesn’t work.

From the comments it seems to be difficult to understand this, so I will repeat: There is no rule that determines this automatic conversion, it only works if it is explicit.

It would be enough to have a rule that determined that this was done by the compiler that would work. The language developers thought it was not desirable, probably because they thought it could happen by accident.

*This idea of primitive will get complicated when Java has basic data so it is not primitive (and will soon). And I want to see how they’ll handle casting since they have decided not to have operator overload, will change their mind or will be something more capenga?

  • I understand that there are rules of self-promotion between primitives and I understand the difference between primitive and wrapper. I know that when we use a literal to initialize a wrapper, an autobox occurs. By the definition of autobox, the compiler replaces a literal value by nameDoWrapperDoPrimitivo.valueOf(literal), as shown in the example. My doubt is at this point. Doing explicitly, it compiles because valueOf has overload to double, I know that the whole value undergoes auto-romotion to double automatically. I don’t understand why this isn’t working implicitly.

  • What is not working implicitly?

  • Double d = 10; //implicit, not working, Double d = Double.valueOf(10); // explicitly, it works, the compiler uses the autobox concept here according to the documentation.

  • It’s explained in the answer why you can’t do it.

  • The documentation says that when using a primitive to define a wrapper value an autobox occurs. According to the autobox, the compiler arrives at the line Double d = 10; and switches to Double d = Double.valueOf(10);, so it is possible to work with primitives and Wrappers. The point is that for the case I put it does not work. You addressed other alternatives, I agree. The question is AUTOBOX.

  • What documentation? Autobox is a thing, autocast is another. In the examples the question is asking * autobox* or autocast, in the example of the question nor tries to ask autobox because first I would need to make a cast, that was not done. And the answer makes it clear that it does not automatically.

  • Exact. Autoboxing only works with primitive 'correspondents''

  • I’ve never heard this term: "self-promotion"

  • @Brunosilva how would translate type autocasting?

  • @bigown In the case below I know as magnification "This is because there are rules in the language of self-promotion of compatible types only among the primitive types of the language. Works: double D1 = 10;"

  • @Brunosilva and how would you translate magnification into English? The term does not seem to imply that it is automatic. Enlargement can even be synonymous with promotion. In English I see a lot the "Promote*, Amplifier or something like that I’ve never seen. Anyway, it might just be a case Lost in Translation, ... or not :)

  • It’s rs. I have little experience in the field, just how I learned, but what is it... rs

Show 7 more comments

1

All that has already been explained, the answer is this: No enlargement for wrapper, it is not possible to perform magnification and Boxing at the same time. So first you need to perform the cast for the autoboxing to work.

Double dWrap = (double) 10; // primeiro cast, depois autoboxing

double dPrim = 1; // Ampliação - ocorre apenas entre primitivos

double is greater than int, therefore the term 'enlargement'.

Tamanho dos Tipos

Browser other questions tagged

You are not signed in. Login or sign up in order to post.