您当前的位置: 首页 >  Java

星拱北辰

暂无认证

  • 0浏览

    0关注

    1205博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

【Java】关键词strictfp解析

星拱北辰 发布时间:2020-02-29 18:55:39 ,浏览量:0

Java为何要引入strictfp

strictfp是Java中的一个关键字,全称 strict float point (精确浮点),用于限制浮点计算并在执行浮点变量操作时确保每个平台上的结果相同。

浮点计算与平台有关,即在不同平台(16/32/64位处理器)上运行类文件时,可以实现不同的输出(浮点值)。为了解决这类问题,在JDK1.2版本中引入了strictfp关键字,遵循IEEE754标准进行浮点计算。(也许可能真的有人不知道IEEE754,那就建议自行了解咯~)

如果你想让你的浮点运算更加精确,而且不会因为不同的硬件平台所执行的结果不一致的话,推荐使用关键字strictfp。

strictfp与Java方法 strictfp与普通方法

下面代码的calMoney()被strictfp修饰了,那就表示这个方法会遵照strictfp的“要求”。

public class Coffee {   
    
    private double price;
    
    private double weight;
    
    public Coffee(double price, double weight) {
        this.price = price;
        this.weight = weight;
    }
    
    public strictfp double calMoney() {
        return price*weight;
    }
    
    //setters and getters
    
}
strictfp与抽象方法

strictfp绝对不能用于抽象方法!!!会编译错误的!!!

public interface ICalculate {   

    strictfp double multiply();
     
}

上面的代码就是使用了strictfp修饰接口中的抽象方法,编译错误!!!

在这里插入图片描述

strictfp与Java类 strictfp与普通类

当使用strictfp修饰符声明类时,那么在类中声明的所有方法以及在该类中声明的所有嵌套类型都隐式被strictfp修饰。

public strictfp class Coffee {   
    
    private double price;
    
    private double weight;
    
    public Coffee(double price, double weight) {
        this.price = price;
        this.weight = weight;
    }
    
    public double calMoney() {
        return price*weight;
    }
    
    //setters and getters
    
}

如上代码,calMoney() 虽然没有直接被 strictfp 修饰,但由于Coffee这个类被 strictfp 修饰了,所以实际上 calMoney() 还是被strictfp修饰了。

strictfp与抽象类

strictfp 可以用于抽象类,在抽象类被继承,其中的抽象方法被实现的时候会默认使用 strictfp 修饰。

但是,前面说过,strictfp 不能用于抽象类中抽象方法的修饰,再次强调!!!

public abstract strictfp class AbstractCoffee {   
    
    private double price;
    
    public Coffee(double price) {
        this.price = price;
    }
    
    public abstract double calculate();
    
    //setters and getters
    
}
public class Coffee extends AbstractCoffee {   
    
    private double weight;
    
    public Coffee(double price, double weight) {
        super(price);
        this.weight = weight;
    }
    
    public double calculate() {
        return getPrice()*weight;
    }
    
    //setters and getters
    
}
strictfp与接口

strictfp 可以用于接口,在接口被实现,其中的抽象方法也被实现的时候会默认使用 strictfp 修饰。

但是,前面说过,strictfp 不能用于接口中抽象方法的修饰,再次强调!!!

public strictfp interface ICalculate {   

    double multiply();
     
}

如上代码,multiply()虽然没有被(事实上也不能被)strictfp修饰,但下面的multiply()方法就默认了这一点:

public class Coffee implements ICalculate {   
    
    private double price;
    
    private double weight;
    
    public Coffee(double price, double weight) {
        this.price = price;
        this.weight = weight;
    }
    
    public double multiply() {
        return price*weight;
    }
    
    //setters and getters
    
}

上面的Coffee类没有被strictfp修饰,multiply()方法也没有被strictfp修饰,但由于multiply()是从ICalculate接口继承过来的,所以默认带上了strictfp的修饰。

抽象类中,strictfp只是不能修饰抽象方法,普通方法不受限。但由于接口的方法是隐式抽象的,因此其实strictfp 不能用于接口内的任何方法!!!!

strictfp的功能测试
public class StrictfpTest {

    private static strictfp double add(float a, double b) {
        return a+b;
    }

    public static void main(String[] args) {
        System.out.println(0.6710339+0.04150553411984792);
        System.out.println(add(0.6710339f, 0.04150553411984792));
    }
    
}

测试结果:

0.7125394341198479
0.7125394529774224
strictfp是高精的吗

答案是:No!!!绝对不是!!!

strictfp只是保证浮点运算都严格按照IEEE754进行,保证了各种平台下浮点运算规则的统一,并不是确保了高精。

比如3*0.1,如果我没记错的话,你就算使用strictfp也不能精确得到0.3,更何况高精运算。

高精运算如果能使用轮子的话就用java.math.BigDecimal吧!

关注
打赏
1660750074
查看更多评论
立即登录/注册

微信扫码登录

0.0418s