Use Advanced Search to search the entire archive.
Re: Email proposal to the core-libs-dev@openjdk.java.net
- From: Otávio Gonçalves de Santana <
>
- To:
- Subject: Re: Email proposal to the
- Date: Tue, 28 Oct 2014 20:46:13 -0200
The problem is you are looking to actual implementation, maybe if we used
best strategies with generics it will not happen. About multiply units, in
this time the Erasable effect work to help us.
But I know, the focus is ME and not SE, so go a head, maybe we can submit
it to SE to Java 10 (when I hope the generics get more maturity).
On Tue, Oct 21, 2014 at 10:34 AM, Martin Desruisseaux <
>
wrote:
>
Hello Otávio
>
>
Le 21/10/14 19:12, Otávio Gonçalves de Santana a écrit :
>
>
Martin, in your example can happen ClassCastException, in our case not,
>
because we are using the same interface.
>
>
In my example a ClassCastException can happen here:
>
>
Integer r = (Integer) multiply(x, y);
>
>
An no ClassCastException can happen here (potentially wrongly):
>
>
Comparable<Integer> r = (Comparable<Integer>) multiply(x, y); // Unsafe
>
cast
>
>
In your example a ClassCastException can happen here (choose the
>
alternative you prefer):
>
>
Length r = (Length) speed.multiply(time);
>
Length r = speed.multiply(time).cast(Length.class);
>
>
An no ClassCastException can happen here (potentially wrongly):
>
>
Quantity<Length> r = (Quantity<Length>) speed.multiply(time); // Unsafe
>
cast
>
>
Where do you see a behavioural difference? And what do you mean by
>
"because we are using the same interface"? In my example too all classes
>
extends Comparable, and all arguments and return value are Comparable.
>
>
>
I did a brief of the code below, I am just using Generics with diamond
>
resources, available in Java 7 or above. Can you show me how may happen the
>
same thing with this code or the cast could be unsafe?
>
>
Yes. Here:
>
>
public class BigDecimalQuanity<Q extends Quantity<Q>> implements
>
Quantity<Q> {
>
public <T extends Quantity<T>, E extends Quantity<E>> Quantity<E>
>
multiply(Quantity<T> that) {
>
return new BigDecimalQuanity<>();
>
}
>
}
>
>
The compiler accepts this code because you are not assigning any unit to
>
BigDecimalQuantity. If you try to assign a Unit<E> to that
>
BigDecimalQuantity, you are faced to the following problems:
>
>
- The parameterized type of Quantity unit is the same as the
>
parameterized type of the quantity.
>
- Consequently, the parameterized type of the unit of the
>
BigDecimalQuantity you are constructing must be <E>.
>
- The parameterized type of the Unit computed by that multiply
>
function is <?> (attempts to "fix" Unit.multiply(Unit) will just lead
>
to a similar bullet list than this one).
>
- That multiply method has absolutely no way to know that the Unit<?>
>
can be safely casted to Unit<E>. The only way to verify that in
>
current Java would be to have a Class<E> argument.
>
- Consequently multiply can not proceed, end of the story.
>
>
Even if we could check the type inside the multiply method, this is not
>
the way parameterized types are supposed to work. Except for a few
>
special-purpose methods like Class.asSubclass(Class) or Unit.asType(Class),
>
The purpose of parameterized type is to guarantee that no
>
ClassCastException will be thrown if the error compiled without errors
>
and without "unsafe cast warnings".
>
>
I challenge you to write a complete multiply implementation with your
>
method signature without "unsafe cast" warning that you can not prove to be
>
safe. If you succeed, I retire everything I told in this whole threat,
>
would own you all my apologize, send flowers, ton of chocolate, wash your
>
car, etc.
>
>
The fact that a method is impossible to implement without unprovable
>
"unsafe cast" warnings is a much, much more serious sign of critical design
>
flaw than the presence of <?> in a return value.
>
>
Martin
>
>
--
Otávio Gonçalves de Santana
blog:
http://otaviosantana.blogspot.com.br/
twitter:
http://twitter.com/otaviojava
site: *
http://about.me/otaviojava <
http://about.me/otaviojava>*
55 (11) 98255-3513