2008-10-23 10 views
10

Bu amaçla herhangi bir kütüphane işlevi var mı, bu yüzden TDWTF'de elle ve risk sonlandırma yapmıyorum?PHP'de bir bcmath numarası nasıl yuvarlaklanır/döşenir?

echo ceil(31497230840470473074370324734723042.6); 

// Expected result 
31497230840470473074370324734723043 

// Prints 
<garbage> 
+0

Ayrıca bkz benim ilgili soru: http://stackoverflow.com/questions/1642614/how-to-ceil-floor-and-round-bcmath-numbers –

cevap

7

Bu sizin için çalışacaktır:

$x = '31497230840470473074370324734723042.9'; 

bcscale(100); 
var_dump(bcFloor($x)); 
var_dump(bcCeil($x)); 
var_dump(bcRound($x)); 

function bcFloor($x) 
{ 
    $result = bcmul($x, '1', 0); 
    if ((bccomp($result, '0', 0) == -1) && bccomp($x, $result, 1)) 
     $result = bcsub($result, 1, 0); 

    return $result; 
} 

function bcCeil($x) 
{ 
    $floor = bcFloor($x); 
    return bcadd($floor, ceil(bcsub($x, $floor)), 0); 
} 

function bcRound($x) 
{ 
    $floor = bcFloor($x); 
    return bcadd($floor, round(bcsub($x, $floor)), 0); 
} 

Temelde sıfır hassasiyetle teker çarpılarak flooy bulur.

Sonra sonra, yerleşik işlev çağrısında toplamda o çıkararak

düzenle geri sonucunu ekleyerek ceil/yuvarlak yapabilirsiniz: -ve sayılar için

+0

1 Ancak, davranış ölçeğe bağlı olduğu için bcCeil ve bcRound için bir ölçek argümanı eklemeye değer olabilir. Eğer bcscale (0) 'adını verirseniz, bcCeil ('1.1') 'i deneyebilirsiniz, beklediğiniz gibi' 1 'değil' 2 'olacaksınız. Ölçeğin belirtilmesine izin vermek, diğer BCMath işlevleriyle tutarlı olacaktır. –

+0

Ayrıca, ölçek argümanının varsayılan değeri boş olmalı ve eğer sağlanmamışsa, 'bcscale' tarafından ayarlanan değerin üzerine yazılmamalıdır. –

13

GÜNCELLEME düzeltildi: Bkz benim Burada geliştirilmiş cevap: How to ceil, floor and round bcmath numbers?.


Bu işlevler en azından bana, daha mantıklı görünmektedir:

function bcceil($number) 
{ 
    if ($number[0] != '-') 
    { 
     return bcadd($number, 1, 0); 
    } 

    return bcsub($number, 0, 0); 
} 

function bcfloor($number) 
{ 
    if ($number[0] != '-') 
    { 
     return bcadd($number, 0, 0); 
    } 

    return bcsub($number, 1, 0); 
} 

function bcround($number, $precision = 0) 
{ 
    if ($number[0] != '-') 
    { 
     return bcadd($number, '0.' . str_repeat('0', $precision) . '5', $precision); 
    } 

    return bcsub($number, '0.' . str_repeat('0', $precision) . '5', $precision); 
} 

Onlar negatif sayılar ve bcround() fonksiyonu için hassas argümanı destekler.

Bazı testler:

assert(bcceil('4.3') == ceil('4.3')); // true 
assert(bcceil('9.999') == ceil('9.999')); // true 
assert(bcceil('-3.14') == ceil('-3.14')); // true 

assert(bcfloor('4.3') == floor('4.3')); // true 
assert(bcfloor('9.999') == floor('9.999')); // true 
assert(bcfloor('-3.14') == floor('-3.14')); // true 

assert(bcround('3.4', 0) == number_format('3.4', 0)); // true 
assert(bcround('3.5', 0) == number_format('3.5', 0)); // true 
assert(bcround('3.6', 0) == number_format('3.6', 0)); // true 
assert(bcround('1.95583', 2) == number_format('1.95583', 2)); // true 
assert(bcround('5.045', 2) == number_format('5.045', 2)); // true 
assert(bcround('5.055', 2) == number_format('5.055', 2)); // true 
assert(bcround('9.999', 2) == number_format('9.999', 2)); // true 
+0

Tam sayılarla çalışmaz. Bu fonksiyonların iyi bir şekilde gerçekleştirilmesi: http://stackoverflow.com/a/1653826/541961 Alix, mesajınızı daha yeni olana bağlamak için düzenleyebilirsiniz. – Dmitriy

+1

@Dmitriy: Bitti. Teşekkürler. –