Java:在不改变其类型的情况下乘以通用数字

时间:2014-11-24 14:24:55

标签: java math numbers

Java中有没有办法实现这种方法?

public static <T extends Number> T doubleOf(T number){
    //I don't know...
}

由于

5 个答案:

答案 0 :(得分:2)

正如其他答案所述,没有一般解决方案。 除了其他人之外,某些Number子类可能无法很好地定义您要实现的操作。例如,AtomicInteger的倍数是多少?它是带有乘法值的同一个实例吗?或者AtomicInteger的新实例?还是一个新的平原Integer?从理论上讲,可能存在Number的子类,它不允许自由创建新实例。

您可以测试某些已知子类的输入并为其执行操作。像这样:

@SuppressWarnings("unchecked")
public static <N extends Number> N multiply(N number, int multiplier) {
    Class<? extends Number> cls = number.getClass();
    if (cls == Integer.class) {
        return (N) Integer.valueOf(number.intValue() * multiplier);
    }
    if (cls == Long.class) {
        return (N) Long.valueOf(number.longValue() * multiplier);
    }
    throw new UnsupportedOperationException("unknown class: " + cls);
}

我担心以某种形式抑制警告是必要的。

答案 1 :(得分:1)

不幸的是,Java无法实现,因为您无法实例化T类型的对象。

请参阅Java泛型教程的这一部分:http://docs.oracle.com/javase/tutorial/java/generics/restrictions.html#createObjects

答案 2 :(得分:1)

有点晚了,但是今天我遇到了同样的问题。

我的解决方案:

public Number multiply(Number number, int multiplier) {
    return new Number() {
        @Override
        public long longValue() {
            return number.longValue() * multiplier;
        }

        @Override
        public int intValue() {
            return number.intValue() * multiplier;
        }

        @Override
        public float floatValue() {
            return number.floatValue() * multiplier;
        }

        @Override
        public double doubleValue() {
            return number.doubleValue() * multiplier;
        }
    };
}

答案 3 :(得分:0)

简单的答案是否定的。 Number没有适当的方法。

但是只要Number有几个众所周知的实现,你就可以为所有这些实现它。当然,如果某人创建了新的实现,那么实现将会失败,但这种可能性很小

public static <T extends Number> T doubleOf(T number){
    if(number instanceOf Integer){
        return (T)(Object)number.intValue()*2;
    } ... and so on
}

答案 4 :(得分:0)

虽然有点奇怪,但您可以使用以下内容:

public static <T extends Number & Multipliable> T doubleOf(T number)
{

}

interface Multipliable<T extends Number>
{
    T multiply(Number number);
}

class MyDouble extends Number implements Multipliable<MyDouble>
{

    Double  d;

    public MyDouble(final double d)
    {
        this.d = new Double(d);
    }

    @Override
    public MyDouble multiply(Number number)
    {
        return new MyDouble(d.doubleValue() * number.doubleValue());
    }

    @Override
    public double doubleValue()
    {
        return d.doubleValue();
    }

    @Override
    public float floatValue()
    {
        return d.floatValue();
    }

    @Override
    public int intValue()
    {
        return d.intValue();
    }

    @Override
    public long longValue()
    {
        return d.longValue();
    }

}

这可以这样使用:

MyDouble result = new MyDouble(2d).multiply(new Short((short) 1));