PHP 부동 소수점 숫자 비교 방법에 대한 설명

jacklove
풀어 주다: 2023-03-31 07:38:01
원래의
1495명이 탐색했습니다.

부동 소수점 연산 정밀도 문제

먼저 예를 살펴보세요.

<?php$a = 0.1;$b = 0.9;$c = 1;
var_dump(($a+$b)==$c);
var_dump(($c-$b)==$a);?>
로그인 후 복사

$a+$b==$c는 true를 반환하고,
$c-$b==$a는 false를 반환하고, error

를 반환합니다.

왜 이런 일이 일어나는 걸까요?
연산 후 정밀도가 20자리일 때 실제 반환되는 내용은 다음과 같습니다.

<?php$a = 0.1;$b = 0.9;$c = 1;
printf("%.20f", $a+$b); // 1.00000000000000000000printf("%.20f", $c-$b); // 0.09999999999999997780?>
로그인 후 복사

$c-$b는 0.09999999999999997780이므로 0.1과 비교하면 false

이 문제가 발생합니다. 정밀도 부동 소수점 숫자를 이진수로 변환할 때 정밀도가 손실될 수 있습니다.

부동 소수점 변환 방법

정수 부분은 2로 나누어 반올림방법
소수 부분은2를 곱하여 반올림방법

예: 숫자 8.5를 다음으로 변환합니다. 이진
정수 부분 8
8/2=4 8%2=0
4/2=2 4%2=0
2/2=1 2%2=0
1은 2보다 작으므로 계산할 필요가 없습니다. 정수는 8입니다. 이진법은 1000

소수 부분은 0.5
0.5x2 = 1.0
반올림 후의 소수 부분은 0이므로 더 이상 계산할 필요가 없습니다
십진수 0.5의 이진법은 0.1

8.5 1000.1

숫자 0.9의 이진수 표현을 계산하세요.
0.9x2=1.8
0.8x2=1.6
0.6x2=1.2
0.2x2=0.4
0.4x2=0.8
0.8x2=1.6
…. 그런 다음 사이클이 계속되고, 차단 정밀도가 N이면 N 다음의 숫자가 반올림되어 정밀도가 손실됩니다.
위의 예에서는 바이너리로 변환하면 정밀도 0.9가 손실되어 비교 시 오류가 발생합니다.

그러므로 부동 소수점 숫자가 마지막 숫자까지 정확하다고 믿지 말고 두 부동 소수점 숫자가 같은지 비교하지 마세요.

부동소수점 수를 올바르게 비교하는 방법

1. 라운드 방식을 사용하여 처리한 후 비교
예:

<?php$a = 0.1;$b = 0.9;$c = 1;
var_dump(($c-$b)==$a);                   // falsevar_dump(round(($c-$b),1)==round($a,1)); // true?>
로그인 후 복사


2. 연산을 먼저 수행할 때 , 높은 정밀도를 사용하십시오. 계산 방법은 정확성을 잃지 않도록 보장할 수 있습니다.

고정밀도 연산 방법은 다음과 같습니다.

bcadd
두 개의 고정밀도 숫자를 더합니다. bccomp
두 개의 고정밀도 숫자를 비교하여 -1,0,1을 반환합니다. bcp
두 개의 고정밀도 숫자를 더합니다. -정밀도 숫자 숫자 나누기bcmod
고정밀 숫자의 나머지를 구합니다bcmul
두 고정밀 숫자를 곱합니다bcpow
고정밀 숫자의 거듭제곱을 찾습니다bcpowmod
모듈러스를 찾습니다. 고정밀 숫자의 거듭제곱bcscale
구성 기본값 소수점 이하 자릿수는 Linux bc의 "scale="과 동일합니다. bc bcsqrt
고정밀 숫자의 제곱근을 구합니다bcsub
두 개의 고정밀 숫자를 뺍니다. 정밀 숫자예:

<?php$a = 0.1;$b = 0.9;$c = 1;
var_dump(($c-$b)==$a);          // falsevar_dump(bcsub($c, $b, 1)==$a); // true?>
로그인 후 복사

이 문서에서는 PHP 부동 소수점 숫자 비교 방법에 대해 설명합니다. 더 많은 관련 내용을 보려면 PHP 중국어 웹사이트를 참조하세요.

관련 추천:

mysql을 통해 쿼리 결과를 csv로 내보내는 방법 설명


php array_push와 $arr[]=$value


PHP를 사용하여 설정하는 방법 만료 시간이 있는 엄격한 제어 세션

위 내용은 PHP 부동 소수점 숫자 비교 방법에 대한 설명의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿