1701005389
1701005390
我们都知道计算机是二进制存储数据的,由于0.1没有精确的IEEE编码,根据就近一致原则,0.1采用的IEEE编码就采用最近的第二个编码。
1701005391
1701005392
【问题】0.1两个编码到底代表什么数据呢?
1701005393
1701005394
【分析】
1701005395
1701005396
下面使用ieee2double()函数来测试如下:
1701005397
1701005398
clc,clear,close all %清屏和清除变量 warning off %消除警告 x_double_01_left=ieee2double(‘0011111110111001100110011001100110011001100110011001100110011001’) %将IEEE编码转换为双精度数据 ans1 = double(x_double_01_left)-0.1 %可以看出,第一个IEEE编码和0.1还是有差距的 x_double_01_right=ieee2double(‘0011111110111001100110011001100110011001100110011001100110011010’) ans2 = double(x_double_01_right)-0.1 %第二个IEEE编码和0.1就没有区别了
1701005399
1701005400
运行程序输出结果如下:
1701005401
1701005402
x_double_01_left = 7205759403792793/72057594037927936 ans1 = -1.3878e-17 x_double_01_right = 3602879701896397/36028797018963968 ans2 = 0
1701005403
1701005404
由结果可以看出,第一个IEEE编码和0.1还是有差距的;第二个IEEE编码和0.1没有区别,然而它也不是0.1的真实编码,而是距离最近的一个,换句话说0.1是没有准确的IEEE编码的,当然还有很多数据也没有准确的IEEE编码。
1701005405
1701005406
同理可以得到0.2和0.3的IEEE编码,以及相应的IEEE编码代表的真实数值,程序如下:
1701005407
1701005408
%0.2的编码转换 clc,clear,close all %清屏和清除变量 warning off %消除警告 x_ieee_02=double2ieee(0.2) %0.2 IEEE编码 x_double_02=ieee2double(x_ieee_02) %0.3的编码转换 x_ieee_03=double2ieee(0.3) %0.3 IEEE编码 x_double_03=ieee2double(x_ieee_03)
1701005409
1701005410
运行程序输出结果如下:
1701005411
1701005412
x_ieee_02 = 0011111111001001100110011001100110011001100110011001100110011010 x_double_02 = 3602879701896397/18014398509481984 x_ieee_03 = 0011111111010011001100110011001100110011001100110011001100110011 x_double_03 = 5404319552844595/18014398509481984
1701005413
1701005414
现在模拟计算0.1+0.3-0.2的结果:
1701005415
1701005416
x_double_01-x_double_03+x_double_02
1701005417
1701005418
运行程序输出结果如下:
1701005419
1701005420
ans = 1/36028797018963968
1701005421
1701005422
对输出结果求其导数如下:
1701005423
1701005424
1/36028797018963968
1701005425
1701005426
运行程序输出结果如下:
1701005427
1701005428
ans = 2.7756e-17
1701005429
1701005430
然后直接采用MATLAB输入0.1-0.3+0.2进行数值模拟,程序如下:
1701005431
1701005432
>> 0.1-0.3+0.2 ans = 2.7756e-17
1701005433
1701005434
也就是说,在IEEE标准下,0.1+0.3-0.2=1/36028797018963968≈2.7756e-17,显然这个不等于0。
1701005435
1701005436
【问题】为什么0.1-0.3+0.2和0.1+0.2+0.3的结果不一样?
1701005437
1701005438
【分析】
[
上一页 ]
[ :1.701005389e+09 ]
[
下一页 ]