54

PHPの小数点以下を小数点以下2桁に切り捨てて、次のようにする必要があります。

49.955

になります...

49.95

number_formatを試しましたが、これは値を49.96に丸めるだけです。数値が小さい可能性があるため(7.950など)、substrを使用できません。私はこれまでこれに対する答えを見つけることができませんでした。

どんな助けでも大歓迎です。

4

16 に答える 16

100

これは機能します:floor($number * 100) / 100

于 2012-09-05T09:13:14.403 に答える
24

残念ながら、以前の回答(受け入れられたものを含む)のいずれも、すべての可能な入力に対して機能しません。

1)sprintf('%1.'.$precision.'f', $val)

精度2で失敗:14.239は14.23を返す必要があります(ただし、この場合は14.24を返します)。

2)floatval(substr($val, 0, strpos($val, '.') + $precision + 1))

0の精度で失敗:14は14を返す必要があります(ただし、この場合は1を返します)

3)substr($val, 0, strrpos($val, '.', 0) + (1 + $precision))

0の精度で失敗します:-1は-1を返す必要があります(ただし、この場合は'-'を返します)

4)floor($val * pow(10, $precision)) / pow(10, $precision)

私はこれを広範囲に使用しましたが、最近、欠陥を発見しました。一部の値でも失敗します。精度が2の場合:2.05は2.05を返す必要があります(ただし、この場合は2.04を返します!!)

これまでのところ、すべてのテストに合格する唯一の方法は、残念ながら文字列操作を使用することです。Rationalbossの1つに基づく私の解決策は、次のとおりです。

function floorDec($val, $precision = 2) {
    if ($precision < 0) { $precision = 0; }
    $numPointPosition = intval(strpos($val, '.'));
    if ($numPointPosition === 0) { //$val is an integer
        return $val;
    }
    return floatval(substr($val, 0, $numPointPosition + $precision + 1));
}

この関数は、正の数と負の数、および必要な精度で機能します。

于 2014-10-21T16:19:22.537 に答える
22

これは、文字列関数を使用せずにトリックを実行する優れた関数です。

<?php
function floorp($val, $precision)
{
    $mult = pow(10, $precision); // Can be cached in lookup table        
    return floor($val * $mult) / $mult;
}

print floorp(49.955, 2);
?>

もう1つのオプションは、丸める前に小数部を減算することです。

function floorp($val, $precision)
{
    $half = 0.5 / pow(10, $precision); // Can be cached in a lookup table
    return round($val - $half, $precision);
}
于 2012-09-05T09:12:38.297 に答える
11

これを達成するための非常に簡単な方法があると思います。

$rounded = bcdiv($val, 1, $precision);

これが実際の例です。BCMathをインストールする必要がありますが、通常はPHPインストールにバンドルされていると思います。:)ここにドキュメントがあります

于 2019-03-19T10:48:21.270 に答える
7

入力に100を掛け、floor()してから、結果を100で割ります。

于 2012-09-05T09:13:04.687 に答える
7
function roundDown($decimal, $precision)
{
    $sign = $decimal > 0 ? 1 : -1;
    $base = pow(10, $precision);
    return floor(abs($decimal) * $base) / $base * $sign;
}

// Examples
roundDown(49.955, 2);           // output: 49.95
roundDown(-3.14159, 4);         // output: -3.1415
roundDown(1000.000000019, 8);   // output: 1000.00000001

この関数は、任意の精度で正および負の小数で機能します。

ここでのコード例:http://codepad.org/1jzXjE5L

于 2016-02-20T00:51:49.950 に答える
4

bcdivPHP関数を使用できます。

bcdiv(49.955, 1, 2)
于 2019-03-19T10:55:14.573 に答える
3

round()機能を試す

このような:round($num, 2, PHP_ROUND_HALF_DOWN);

于 2012-09-05T09:10:08.220 に答える
3

困っている人のために、私は数学関数の誤動作を克服するためにちょっとしたトリックを使用しました。たとえば、floorやintval(9.7 * 100)=969奇妙なものです。

function floor_at_decimals($amount, $precision = 2)
{
    $precise = pow(10, $precision);
    return floor(($amount * $precise) + 0.1) / $precise;
}

したがって、少量を追加すると(とにかくフロアになります)、何らかの形で問題が修正されます。

于 2019-11-20T22:39:21.550 に答える
1
function floorToPrecision($val, $precision = 2) {
        return floor(round($val * pow(10, $precision), $precision)) / pow(10, $precision);
    }
于 2019-03-11T10:26:41.103 に答える
0

フォーマットされた出力を使用する

sprintf("%1.2f",49.955) //49.95

デモ

于 2012-09-05T09:09:27.327 に答える
0

次を使用できます。

$num = 49.9555;
echo substr($num, 0, strpos($num, '.') + 3);
于 2012-09-05T09:09:36.183 に答える
0

すべての正または負の数、整数または小数で機能する正規表現を使用する代替ソリューション:

if (preg_match('/^-?(\d+\.?\d{1,2})\d*$/', $originalValue, $matches)){
    $roundedValue = $matches[1];
} else {
    throw new \Exception('Cannot round down properly '.$originalValue.' to two decimal places');
}
于 2017-11-30T20:33:28.647 に答える
0

@huysentruitwと@Alexの回答に基づいて、私はトリックを実行する必要がある次の関数を思いつきました。

それはアレックスの答えで与えられたすべてのテストに合格し(なぜこれが不可能なのか)、huysentruitwの答えに基づいています。

function trim_number($number, $decimalPlaces) {
    $delta = (0 <=> $number) * (0.5 / pow(10, $decimalPlaces));
    $result = round($number + $delta, $decimalPlaces);
    return $result ?: 0; // get rid of negative zero
}

重要なのは、元の番号記号に基づいてデルタを加算または減算し、負の数のトリミングもサポートすることです。最後に、負のゼロ(-0)を取り除くことです。これは、望ましくない動作になる可能性があるためです。

「テスト」遊び場へのリンク

編集:bcdivは行く方法のようです。

// round afterwards to cast 0.00 to 0
// set $divider to 1 when no division is required
round(bcdiv($number, $divider, $decimalPlaces), $decimalPlaces);
于 2019-09-02T12:41:14.777 に答える
-2
sprintf("%1.2f",49.955) //49.95

四捨五入せずに小数を切り捨てる必要がある場合-これは適切ではありません。これは、最後に49.95 5まで正しく機能するためです。たとえば、49.95 7の場合は、49.96
に四捨五入されます。最も普遍的です。

于 2013-10-14T11:14:27.550 に答える
-5

やってみましたround($val,2)か?

round()関数に関する詳細情報

于 2012-09-05T09:08:55.103 に答える