Java 泛型类-运算符问题

Java 泛型类-运算符问题,java,operator-keyword,generics,Java,Operator Keyword,Generics,我正在尝试用Java编写一个泛型类。 通过阅读一些指南,我发现了如何声明它,以及如何调用它的函数 我的类是一个点,如果没有方法,它将是这样的: class Pnt<type>{ protected type x, y; protected int col; } IDE对我大喊大叫,+=对于类型变量是未定义的 我知道在java中不可能定义C++中的一个新操作符,所以我要求用另外一种方法来添加两个类型变量!p> 另外,我将使用的所有类型都是doubleS、floatS和inte

我正在尝试用Java编写一个泛型类。 通过阅读一些指南,我发现了如何声明它,以及如何调用它的函数

我的类是一个点,如果没有方法,它将是这样的:

class Pnt<type>{
  protected type x, y;
  protected int col;
}
IDE对我大喊大叫,
+=
对于
类型
变量是未定义的

<>我知道在java中不可能定义C++中的一个新操作符,所以我要求用另外一种方法来添加两个<代码>类型变量!p>
另外,我将使用的所有类型都是
double
S、
float
S和
int
egers,这就是为什么我试图简单地上瘾。

当你说
classpnt
时,ti意味着
type
是一个对象,而不是像
int
double
这样的原始数据类型。您可以对数值基本数据类型(如
int
float
等)执行
+=
操作,而不是对对象执行操作。事实上,您不能对任何通用对象执行
+=
操作


Integer
Float
等的对象支持
+=
运算符,因为它们是包装类,可以取消绑定到基元类型并在以后自动装箱。但是编译器无法确认
类型
将是
整数
浮点
。因此,它会生成编译时错误。

有两个问题:首先,如果它应该很快,您必须直接使用原语,而这些原语在泛型中不支持作为参数。这实际上意味着您必须分别为
维护三个版本

如果您想使用泛型,可以使用相应的类(如
Integer
),但仍然存在一个问题:它们的超级类型
Number
没有
add
方法(更不用说
+
运算符或
+=

因此,我知道的唯一方法是实现您自己的数字类层次结构,它支持
add
方法:

abstract class Numeric<T extends Number> {
    public abstract T getValue();

    public abstract Numeric<T> add(Numeric<T> other);

    @Override
    public String toString() {
        return getValue().toString();
    }
}

class MyInt extends Numeric<Integer> {
    public final Integer value;

    public MyInt(Integer _value) {
        super();
        this.value = _value;
    }

    @Override
    public Integer getValue() {
        return this.value;
    }

    @Override
    public Numeric<Integer> add(Numeric<Integer> other) {
        return new MyInt(this.value + other.getValue());
    }
}

class MyDouble extends Numeric<Double> {
    public final double value;

    public MyDouble(Double _value) {
        super();
        this.value = _value;
    }

    @Override
    public Double getValue() {
        return this.value;
    }

    @Override
    public Numeric<Double> add(Numeric<Double> other) {
        return new MyDouble(this.value + other.getValue());
    }
}
抽象类数值{
公共抽象T getValue();
公共摘要数字添加(数字其他);
@凌驾
公共字符串toString(){
返回getValue().toString();
}
}
类MyInt扩展了Numeric{
公共最终整数值;
公共MyInt(整数值){
超级();
this.value=_值;
}
@凌驾
公共整数getValue(){
返回此.value;
}
@凌驾
公共数字添加(数字其他){
返回新的MyInt(this.value+other.getValue());
}
}
类MyDouble扩展了数值{
公共最终双重价值;
公共MyDouble(双精度值){
超级();
this.value=_值;
}
@凌驾
公共双getValue(){
返回此.value;
}
@凌驾
公共数字添加(数字其他){
返回新的MyDouble(this.value+other.getValue());
}
}
基于此,您至少可以实现一个通用点:

class NumericPoint<T extends Number> {
    public final Numeric<T> x;
    public final Numeric<T> y;

    public NumericPoint(Numeric<T> _x, Numeric<T> _y) {
        super();
        this.x = _x;
        this.y = _y;
    }

    public NumericPoint<T> add(NumericPoint<T> other) {
        return new NumericPoint<T>(this.x.add(other.x), this.y.add(other.y));
    }

    @Override
    public String toString() {
        return "(" + this.x + "/" + this.y + ")";
    }
}
类数值点{
公共最终数字x;
公共财政;
公共数字点(数字x、数字y){
超级();
this.x=x;
this.y=\u y;
}
公共数字点添加(数字点其他){
返回新的数值点(this.x.add(other.x)、this.y.add(other.y));
}
@凌驾
公共字符串toString(){
返回“(“+this.x+”/“+this.y+”)”;
}
}
配合使用

NumericPoint<Integer> ip1 =
    new NumericPoint<Integer>(new MyInt(1), new MyInt(2));
NumericPoint<Integer> ip2 =
    new NumericPoint<Integer>(new MyInt(3), new MyInt(4));
NumericPoint<Integer> ip = ip1.add(ip2);
System.out.println(ip);

NumericPoint<Double> dp1 = 
  new NumericPoint<Double>(new MyDouble(1.1), new MyDouble(2.1));
NumericPoint<Double> dp2 = 
  new NumericPoint<Double>(new MyDouble(3.1), new MyDouble(4.1));
NumericPoint<Double> dp = dp1.add(dp2);
System.out.println(dp);
数值点ip1=
新的数值点(新的MyInt(1),新的MyInt(2));
数值点ip2=
新的数值点(新的MyInt(3),新的MyInt(4));
数值点ip=ip1.add(ip2);
系统输出打印项次(ip);
数值点dp1=
新数值点(新MyDouble(1.1)、新MyDouble(2.1));
数值点dp2=
新数值点(新MyDouble(3.1)、新MyDouble(4.1));
数值点dp=dp1.add(dp2);
系统输出打印项次(dp);

我修改了你的例子:数字和点是不可变的。例如,它的实现类似于
BigDecimal
。因此,
add
方法属于泛型类,它返回一个新实例。

它也不处理对象类型。事实上,该语句在x+=x_3;时失败;这很奇怪。我想这与原语无关。这就是为什么我必须使用
Double
而不是
Double
等。。。但是对象
Double
Float
Integer
也支持
+=
!是,
Integer
支持
+=
运算符,但编译器无法确认
类型是否为
整数。它可以是
文件
或任何其他类。您可以尝试类似
类Pnt
的方法。我自己还没有测试过,但这表明唯一合法的类是数字,这可能足以让它编译。@chessbot使用`symbol在注释中包装代码。不,使用
type-extends-Number
是不起作用的。请注意,
biginger
(在其他类中)也扩展自
Number
,不支持像
+=
这样的操作。
Integer
Long
和其他包装类支持这一点,这是因为它们自动装箱到基元类型,然后对这些基元执行操作,然后在操作完成后,值再次自动装箱到
Integer
(或您使用的包装类)。重,非常重,我想我会有三个不同的班级来代替。。。不幸的是它不适合我的需要,但是嘿!你让它成为可能=我同意,它很重。它是代码> C++ C++模板>代码C++,解决了这个问题(C++模板允许代码> int /COD>作为模板参数)。
NumericPoint<Integer> ip1 =
    new NumericPoint<Integer>(new MyInt(1), new MyInt(2));
NumericPoint<Integer> ip2 =
    new NumericPoint<Integer>(new MyInt(3), new MyInt(4));
NumericPoint<Integer> ip = ip1.add(ip2);
System.out.println(ip);

NumericPoint<Double> dp1 = 
  new NumericPoint<Double>(new MyDouble(1.1), new MyDouble(2.1));
NumericPoint<Double> dp2 = 
  new NumericPoint<Double>(new MyDouble(3.1), new MyDouble(4.1));
NumericPoint<Double> dp = dp1.add(dp2);
System.out.println(dp);