解决Cannot format given Object as a Number问题,理解DecimalFormat.format()方法及使用DecimalFormat保留两位小数的金额和格式化数字

导读:本篇文章讲解 解决Cannot format given Object as a Number问题,理解DecimalFormat.format()方法及使用DecimalFormat保留两位小数的金额和格式化数字,希望对大家有帮助,欢迎收藏,转发!站点地址:www.bmabk.com

问题

今天在编程时,产品经理突然和我说,把所有的金额保留两位小数后,传递到前台。一时间,不知道该怎么做,于是,通过百度百科,查找到了DecimalFormat这个类。

解释DecimalFormat

DecimalFormatNumberFormat 的一个具体子类,用于格式化十进制数字,如下代码所示:

import java.math.BigDecimal;
import java.text.DecimalFormat;

/**
 * Created By zby on 21:03 2022/5/10
 */
public class StringObject {

    public static void main(String[] args) {
        DecimalFormat decimalFormat = new DecimalFormat("0.00");
        String format = decimalFormat.format(new BigDecimal("2.123"));
        System.out.printf("输出结果为:%s", format);

    }
}

上述代码的输出结果为:

在这里插入图片描述

我们经常使用 DecimalFormat去格式化数字,其中包括金额。

当然,可以通过DecimalFormat(String pattern)去创建当前对象,这里的pattern是设置输出结果的模式。

比如如果输出两位小数,pattern可以为0.00,如上图所示。

若想输出整数,patter可以为0,如下图所示:

在这里插入图片描述

复现问题

但在项目中使用DecimalFormat这个类时,出现了错误,错误如下:

这里写图片描述

通过谷歌翻译得到:无法将给定对象格式化为数字

重点不是这句话,而是为什么无法将给定的对象格式化数字。

这里写图片描述

如果将String类型转化为BigDecimal类型的,就不会报错:

这里写图片描述

为什么会这样呢?

解决问题

通过查看源码得出,DecimalFormat继承了抽象类NumberFormatNumberFormat继承了抽象类Format,里面各有format方法,我们来看看Format类中的format方法

public abstract StringBuffer format(Object obj,
                    StringBuffer toAppendTo,
                    FieldPosition pos);

这是个未实现的方法,我们点击idea左边的向下箭头,会出现让你惊讶的一幕:

这里写图片描述

实现该方法的类有很多,而我们今天所说的就DecimalFormat,我们来看看它的实现方法:

 @Override
    public final StringBuffer format(Object number,
                                     StringBuffer toAppendTo,
                                     FieldPosition pos) {
        if (number instanceof Long || number instanceof Integer ||
                   number instanceof Short || number instanceof Byte ||
                   number instanceof AtomicInteger ||
                   number instanceof AtomicLong ||
                   (number instanceof BigInteger &&
                    ((BigInteger)number).bitLength () < 64)) {
            return format(((Number)number).longValue(), toAppendTo, pos);
        } else if (number instanceof BigDecimal) {
            return format((BigDecimal)number, toAppendTo, pos);
        } else if (number instanceof BigInteger) {
            return format((BigInteger)number, toAppendTo, pos);
        } else if (number instanceof Number) {
            return format(((Number)number).doubleValue(), toAppendTo, pos);
        } else {
            throw new IllegalArgumentException("Cannot format given Object as a Number");
        }
    }

你会发现,我们居然找到了上面报错文字: throw new IllegalArgumentException("Cannot format given Object as a Number");

如果你知道instanceof 的话,你就会明白这是该对象是否是某类的实例化对象。这里的有很多包装类,就没有String类和自定义类型,因而,就会出现了错误。所以,它没办法解释格式化String类型的数据。

总结

遇到报错别紧张,查看源码来解析,建议大家使用idea

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/99260.html

(0)
小半的头像小半

相关推荐

极客之音——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!