[英]how to use generics in Java with language operators and generic class extending Number
I would like to perform an operation on two generics argument of the same type both extending Number.我想对两个相同类型的 generics 参数执行一个操作,它们都扩展了 Number。
Is it Possible?可能吗? I always used to call methods on generic arguments, but seems there is some problem using operators (The operator + is undefined for the argument type(s) T, T).
我总是习惯于在通用 arguments 上调用方法,但使用运算符似乎存在一些问题(对于参数类型 T、T,运算符 + 未定义)。
public static <T extends Number> T sum(T a, T b){
return a+ b;
}
What am I doing wrong?我究竟做错了什么?
EDIT: I try to improve a little bit my question.编辑:我尝试改进一点我的问题。 I understood that operators are not defined for type Number.
我知道没有为 Number 类型定义运算符。 It's a bit sad this thing because it would be nice to perform such an operation without introducing new interfaces like suggested by @Victor Sorokin.
这件事有点可悲,因为如果不引入@Victor Sorokin 建议的新接口,执行这样的操作会很好。
But I still don't understand one thing: if operators are not implemented in the class Number, then at least in Double class should be implemented because I can use + operator with double.但是我仍然不明白一件事:如果 class 号中没有实现运算符,那么至少应该在 Double 中实现 class 因为我可以使用 + 运算符和 double。 Neither these line of code will compile:
这些代码行都不会编译:
public static <T extends Double> T sum(T a, T b){
T c = a +b;
}
why?为什么?
It's not possible because Number
doesn't have a + operator associated with it.这是不可能的,因为
Number
没有与之关联的 + 运算符。 In particular, you can't do this:特别是,您不能这样做:
Number a = new Integer(1);
Number b = new Integer(2);
Number c = a + b;
There is no +
operator for classes in Java (except String and there's implicit conversion for other types via toString()
when one of arguments is String). Java 中的类没有
+
运算符(String 除外,当 arguments 之一是 String 时,通过toString()
对其他类型进行隐式转换)。 So, make you type implement some interface, say所以,让你输入一些接口,比如说
interface Valuable {
// use richest built-in numeric type
double value();
Valuable value(double v);
}
public static <T extends Valuable> T sum(T a, T b){
return a.value(a.value() + b.value());
}
Ugly, isn't it?丑陋,不是吗? =D
=D
Fix 2022 code above is wrong, as Valuable#value
can't produce instance of subtype T
, so we need to go a bit more hairy:修复上面的 2022代码是错误的,因为
Valuable#value
不能产生子类型T
的实例,所以我们需要 go 多毛一点:
interface Valuable<T extends Valuable<T>> {
// use richest built-in numeric type
double value();
T value(double v);
}
class Impl implements Valuable<Impl> {
private final double v;
Impl(double v) {
this.v = v;
}
@Override
public double value() {
return v;
}
@Override
public Impl value(double v) {
return new Impl(v);
}
@Override
public String toString() {
return "Impl{" +
"v=" + v +
'}';
}
}
class Scratch {
public static void main(String[] args) {
Impl a = new Impl(1), b = new Impl(-1);
System.out.println(a + " + " + b + " = " + sum(a, b));
}
public static <T extends Valuable<T>> T sum(T a, T b){
return a.value(a.value() + b.value());
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.