Reputation: 211
I'm trying to make a method that accepts a number of any primitive type (either byte, int, float, long, double or short). Then after a certain checking method either returns that very same number (i.e., for example, it accepts double and returns double) or it returns a zero.
So far I've come to this:
<AnyNumType> AnyNumType cancelAdd(AnyNumType val, String point) {
if (checkModuleMatchAndOff(point) == true) return 0;
else return val;
}
But I get a type mismatch error (with 0 underlined and explained: "Cannot convert from int to AnyNumType"). Is there a way to cope with this zero problem? I intend to use this method in equations so I really need it to return primitive types.
EDIT: Thank you very much for all your replies, guys!
Upvotes: 1
Views: 105
Reputation: 1777
You could change your method type to:
<AnyNumType extends Number> AnyNumType cancelAdd(AnyNumType val, String point);
I don't know exactly what you want do do inside the method, but this should allow you to pass in primitives via auto-boxing.
But it is not generally possible to use generics for primitive types in Java, autoboxing is, I think, the only way.
Returning a value other than the object you got in is possible, but you'd need some ugly reflection and casts, unfortunately. And it would not support all possible types.
(Maybe there is some library for this somewhere?)
For any doubters out there, here's sample code fresh out of Eclipse, without compilation errors, that demonstrates this:
public class NumberGenerix {
@SuppressWarnings("unchecked")
public static <Any extends Number> Any f(Any x) {
Class<?> k = x.getClass();
if (k == Integer.class) {
return (Any) Integer.valueOf(0);
} else if (k == Double.class) {
return (Any) Double.valueOf(0.0);
} else if (k == Long.class) {
return (Any) Long.valueOf(0L);
} else {
// and so on.
throw new RuntimeException("unsupported number type: " + k);
}
}
public static void main(String...args) {
Integer a = f(42);
System.out.println("a == " + a);
Long b = f(42L);
System.out.println("b == " + b);
Double c = f(42.0);
System.out.println("c == " + c);
}
}
Upvotes: 0
Reputation: 178263
No, you're not accepting any primitive type; you're accepting any object type. You may think you're accepting primitive types, but Java generics can use only reference types. Your values are being boxed when passed into this method. You could pass a String
in as val
.
That should indicate why 0
can't be converted to AnyNumType
-- AnyNumType
can be any reference type.
The best way to accept any primitive type is to have overloads for every primitive type, like many methods in the core library do. You can return the equivalent of 0
in each overload, e.g.
byte cancelAdd(byte val, String point)
{
if (checkModuleMatchAndOff(point) == true) return (byte) 0;
else return val;
}
The overloads for the other primitive types will look very similar.
Upvotes: 1