posts - 5,  comments - 0,  views - 3264

项目中遇到了数值运算,如网上所写的,一般有这几个方法:

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
/**
    * 提供精确的加法运算。
    * @param v1 被加数
    * @param v2 加数
    * @return 两个参数的和
    */
    public static double add(double v1, double v2) {
       BigDecimal b1 = new BigDecimal(Double.toString(v1));
       BigDecimal b2 = new BigDecimal(Double.toString(v2));
       return (b1.add(b2)).doubleValue();
    }
    /**
    * 提供精确的减法运算。
    * @param v1 被减数
    * @param v2 减数
    * @return 两个参数的差
    */
    public static double sub(double v1, double v2) {
       BigDecimal b1 = new BigDecimal(Double.toString(v1));
       BigDecimal b2 = new BigDecimal(Double.toString(v2));
        
       return (b1.subtract(b2)).doubleValue();
    }
    /**
    * 提供精确的乘法运算。
    * @param v1 被乘数
    * @param v2 乘数
    * @return 两个参数的积
    */
    public static double mul(double v1, double v2) {
       BigDecimal b1 = new BigDecimal(Double.toString(v1));
       BigDecimal b2 = new BigDecimal(Double.toString(v2));
       return (b1.multiply(b2)).doubleValue();
    }
/**
    * 提供(相对)精确的除法运算。当发生除不尽的情况时,由scale参数指
    * 定精度,以后的数字四舍五入。
    * @param v1 被除数
    * @param v2 除数
    * @param scale 表示需要精确到小数点以后几位。
    * @return 两个参数的商
    */
    public static double div(double v1, double v2, int scale) {
       if (scale < 0) {
        System.err.println("除法精度必须大于0!");
        return 0;
       }
       BigDecimal b1 = new BigDecimal(Double.toString(v1));
       BigDecimal b2 = new BigDecimal(Double.toString(v2));
       return (b1.divide(b2, scale, BigDecimal.ROUND_HALF_UP)).doubleValue();
    }   

 

但是这里,我还有两个地方需要做一些变化:

1、乘法运算需要做精度的四舍五入

2、double会自动进行科学计数法

 

对于第一点新增mul方法

1
2
3
4
5
public static double mul(double v1, double v2,int scale) {
           BigDecimal b1 = new BigDecimal(Double.toString(v1));
           BigDecimal b2 = new BigDecimal(Double.toString(v2));
           return (b1.multiply(b2).setScale(scale, RoundingMode.HALF_UP)).doubleValue();
        }

这样就可以对所做的运算进行需要的精度的四舍五入

第二点新增double2Str方法

1
2
3
4
private static String double2Str(double number)
    {
        return DecimalFormat.getInstance().format(number).replace(",","");   
    }

不需要进行格式化,因为项目中把科学计数法的数字传给客户端.Net接收,无法正确转换成数值(除非客户端特殊处理这个科学计数法数值)

当时,对第一点做了一个错误的精度处理:MathContext

1
2
3
4
public static double mul(double v1, double v2,int scale) {
           BigDecimal b1 = new BigDecimal(Double.toString(v1));
           BigDecimal b2 = new BigDecimal(Double.toString(v2));
        

return b1.multiply(b2, new MathContext(scale,RoundingMode.HALF_UP)).doubleValue();

1
2
    
}

这个MathContext是从左边第一个数开始算起,而不是从小数点后开始算

 

补充一下舍入RoundingMode

在RoundingMode中HALF_DOWN 没有按照我预期的对数值进行向下取数值有点疑惑

 

1
2
double d3 = 102207767.555;
d3=new BigDecimal(d3).setScale(2,RoundingMode.HALF_DOWN).doubleValue();

打印后d3显示102207767.56 不应该是102207767.55?

1
  

ROUND_CEILING
Rounding mode to round towards positive infinity.
向正无穷方向舍入
ROUND_DOWN
Rounding mode to round towards zero.
向零方向舍入
ROUND_FLOOR
Rounding mode to round towards negative infinity.
向负无穷方向舍入

ROUND_HALF_DOWN

Rounding mode to round towards "nearest neighbor" unless both neighbors are equidistant, in which case round down.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向下舍入, 例如1.55 保留一位小数结果为1.5
ROUND_HALF_EVEN
Rounding mode to round towards the "nearest neighbor" unless both neighbors are equidistant, in which case, round towards the even neighbor.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,如果保留位数是奇数,使用ROUND_HALF_UP ,如果是偶数,使用ROUND_HALF_DOWN
ROUND_HALF_UP
Rounding mode to round towards "nearest neighbor" unless both neighbors are equidistant, in which case round up.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向上舍入, 1.55保留一位小数结果为1.6

ROUND_UNNECESSARY

Rounding mode to assert that the requested operation has an exact result, hence no rounding is necessary.
计算结果是精确的,不需要舍入模式
ROUND_UP
Rounding mode to round away from zero.
向远离0的方向舍入

posted @ 2014-01-04 17:02 victor321 阅读(508) 评论(0) 推荐(0)
摘要: private ControlTemplate SetControlTemplate(string color) { FrameworkElementFactory fe = new FrameworkElementFactory(typeof(CustomBorder), "CustomBorder"); fe.SetValue(Bord... 阅读全文
posted @ 2013-03-27 22:22 victor321 阅读(582) 评论(0) 推荐(1)
摘要: 正如在前面所提到的,绑定大数据量的情况下,通过store procedure的方式来查询数据,这种方式由于比较慢,还有一点就是数据量过大,一下子绑定到datagrid中就会导致页面卡死的情况。无奈~~ ria service 中可以通过webconfig来设置超时时间<basicHttpBinding> <binding name="MyBasicHttpBinding" closeTimeout="00:10:00" openTimeout="00:10:00" sendTimeout="00:10:00 阅读全文
posted @ 2011-10-27 00:17 victor321 阅读(458) 评论(0) 推荐(0)
摘要: 代码中所访问到的数据量比较庞大,10w以上,以后导入正式数据估计更大,ria service 获取数据很慢,容易报错,所以,不得不想办法。想学习asp.net的那种方式,直接在storeprocedure里面来进行操作,但是网上几乎找不到这样的方式。提供的参考文章:http://forums.silverlight.net/p/151053/337571.aspx,http://forums.silverlight.net/p/151053/337571.aspx,还没实践,也考虑过在server端分页的方式,直接Skip((pageNum-1)*pageSize).Take(pageSiz. 阅读全文
posted @ 2011-10-22 16:45 victor321 阅读(351) 评论(0) 推荐(0)
摘要: 刚开始遇到的一个问题是这样的,我有一个datagrid,根据不同的条件可以绑定上不同的数据源,或者根据同一个数据源,所要展示的数据字段是不一样的,所以我不能再xaml中把字段给写死了,我第一想到的方法如下:ds_t.fake_proc_T_AP_PMs.Clear(); ds_t.Load(ds_t.Proc_T_AP_PMQuery("2011-07-01", "2011-10-10", cbb_method.SelectedIndex), (lo)=> { ... 阅读全文
posted @ 2011-10-21 18:12 victor321 阅读(617) 评论(0) 推荐(1)
点击右上角即可分享
微信分享提示