项目中保留两位小数四舍五入遇到精度问题:

$num = 0.99;

$num1 = round($num, 2);//0.98999999999999999

$num2 = floatval($num);//0.98999999999999999

目前解决方案:

sprintf("%.2f", round($money, 2));//会自动四舍五入

echo substr(sprintf("%.3f",$n), 0, -1);//不四舍五入

测试结果:

var_dump(json_encode(round(0.99 ,2)));//0.98999999999999999

var_dump(round(0.99 ,2));//0.99

$f = 0.58;

var_dump(intval($f * 100));//57

关于等于57这个问题,我们可以分析一下:

浮点数的表示(IEEE 754:IEEE二进位浮点数算术标准):

浮点数, 以64位的长度(双精度)为例, 会采用1位符号位(E), 11指数位(Q), 52位尾数(M)表示(一共64位).

符号位:最高位表示数据的正负,0表示正数,1表示负数。

指数位:表示数据以2为底的幂,指数采用偏移码表示

尾数:表示数据小数点后的有效数字.

0.58 对于二进制表示来说, 是无限长的值:

0.58的二进制表示基本上(52位)是: 0010100011110101110000101000111101011100001010001111

0.57的二进制表示基本上(52位)是: 001000111101011100001010001111010111000010100011110

而两者的二进制, 如果只是通过这52位计算的话,分别是:

0.58 –> 0.57999999999999996

0.57 –> 0.5699999999999999

所以,0.58 * 100 结果会:57.999999999,转成整型:57

关于浮点数的二进制表示可以参考:浮点数的二进制表示

类似:

(0.1 + 0.7) == 0.8//false

floor((0.1+0.7)*10)//7

//内部结果可能是:7.9999999999

//所以:不可能精确的用有限位数表达某些十进制分数

1/3=3.33333333333

//而3.333333333333333*3,却不是1

所以结论:

所以永远不要相信浮点数结果精确到了最后一位,也永远不要比较两个浮点数是否相等。如果确实需要更高的精度,应该使用任意精度数学函数或者 gmp 函数

建议使用高精度函数:

bcadd — 2个任意精度数字的加法计算

bccomp — 比较两个任意精度的数字

bcdiv — 2个任意精度的数字除法计算

bcmod — 对一个任意精度数字取模

bcmul — 2个任意精度数字乘法计算

bcpow — 任意精度数字的乘方

bcpowmod — Raise an arbitrary precision number to another, reduced by a specified modulus

bcscale — 设置所有bc数学函数的默认小数点保留位数

bcsqrt — 任意精度数字的二次方根

bcsub — 2个任意精度数字的减法

使用高精度函数实现四舍五入:

function getBcRound($number, $precision = 0)

{

$precision = ($precision

? 0

: (int) $precision;

if (strcmp(bcadd($number, '0', $precision), bcadd($number, '0', $precision+1)) == 0) {

return bcadd($number, '0', $precision);

}

if (getBcPresion($number) - $precision > 1) {

$number = getBcRound($number, $precision + 1);

}

$t = '0.' . str_repeat('0', $precision) . '5';

return $number

? bcsub($number, $t, $precision)

: bcadd($number, $t, $precision);

}

function getBcPresion($number) {

$dotPosition = strpos($number, '.');

if ($dotPosition === false) {

return 0;

}

return strlen($number) - strpos($number, '.') - 1;

}

$money = getBcRound(0.99, 2);

PHP读取表格都是精度,php 小数精度问题相关推荐

  1. php获取excel表格内容,利用PHPExcel如何读取表格中内容

    利用PHPExcel如何读取表格的内容呢?话不多说,下面的这篇文章将给大家详细的介绍关于PHPExcel读取表格中内容的方法. 先引入类IOFactory.phprequire_once '../PH ...

  2. 用camelot读取表格_如何使用Camelot从PDF提取表格

    用camelot读取表格 数据科学 (DATA SCIENCE) 安装 (Installation) If you are on Windows make sure to install Ghosts ...

  3. Sql Decimal类型 运算结果的精度和小数位数

    最近遇到一个问题,定义了三个Decimal(24,12)类型的变量,如: declare @operand1 Decimal(24,12),@operand2 Decimal(24,12),@oper ...

  4. MATALB实践分享——批量读取表格文件

    Matlab应用笔记--批量读取Excel文件 小树不修不直溜,人不学习哏啾啾.各位家人们都还好吗,今年的三月注定又是个今生难忘的春季,不知道多少朋友和本喵一样在"封闭抗疫".又有 ...

  5. PHPExcel读取表格内容

    PHPExcel读取表格 --- 先引入类IOFactory.php require_once '../PHPExcel/IOFactory.php';$filePath = "test.x ...

  6. Laravel的excel读取表格内存溢出解决方案

    技术栈:php laravel maatwebsite/excel 问题描述 :用户上传excel表格,php程序读取表格数据,由于表格不规范出现大量空行数据(列和行都存在同样的问题),导致读取表格数 ...

  7. arcgis gdb新建浮点型字段不能设置精度和小数位数

    今天协助客户测试的时候发现这么一个问题arcgis gdb库新建浮点型字段不能设置精度和小数位数, 这是在gdb中新建字段 我们可以在字段属性中进行设置 但是这种也只是相当于设置值在字段的显示效果,并 ...

  8. JS 小数精度完美解决(前提是已知小数位数)

    JS 小数精度完美解决(前提是已知小数位数) 前端JavaScript语言在小数运算时经常出现小数精度缺失,现在对已知小数位数的运算解决方法记录一下 以两位小数举例: var a = 1.02 var ...

  9. Odoo小数精度及货币精度详解

    一.小数精度的设置 一般在设置-数据结构-精度设置中就可以对 小数类型的字段进行精度设置: 对于代码中定义为 digits=dp.get_precision('Product Price') 或 di ...

最新文章

  1. android插件化-apkplug中以监听方式获取OSGI服务-09
  2. jQuery 2.0.3 源码分析 Deferred(最细的实现剖析,带图)
  3. MyCP(课下作业,必做)
  4. C#LeetCode刷题之#507-完美数(Perfect Number)
  5. Win 10 Revit 2019 安装过程,亲自踩的一遍坑,有你想要的细节
  6. 阿里完成首个可控量子比特研发;45 名谷歌员工举报不公对待;Swoft 2.0.6 正式版发布 | 极客头条...
  7. mongodb教程_MongoDB教程
  8. Rootkit之ntrootkit的配置使用
  9. 怎样在photoshop中快速批量,修改图片
  10. ee er_英语单词说文解字—第32节 后缀er和ee的构词
  11. cuteftp下载文件变成macintosh格式
  12. 关于求两个球相交部分体积计算
  13. 子寅:不会“怼”产品经理,干不了程序员,更干不好脱口秀
  14. AutodeskCAD卸载后无法再次安装?完美解决!
  15. python: format
  16. Python 实现延时队列
  17. 「案例」如何解决公司采购与财务之间的工作矛盾?
  18. undo_retentionguarantee
  19. STC8H运行smallRTOS51操作系统(1)
  20. 计算机专业系统文献,计算机系统参考文献

热门文章

  1. PHP计算计算时间差,php中计算时间差的几种方法
  2. mbot编程机器人怎么连接蓝牙_台式机蓝牙怎么连接
  3. 2018年5大微服务发展趋势
  4. MFC中 给基于CFormView的单文档添加背景图片
  5. [leetcode]Flatten Binary Tree to Linked List
  6. srt乱码字幕中文显示解决办法
  7. Android-JNI开发系列《六》jni与java的交互
  8. Git (10)-- 打标签(git tag)
  9. QT之Win10安装(五)
  10. Audition生成扫频信号(四十)