Skip to content
This repository was archived by the owner on Dec 27, 2023. It is now read-only.

Commit 16d7ec5

Browse files
committed
Added isInteger method to Decimal, taking advantadge of DecimalConstants
1 parent 9370327 commit 16d7ec5

File tree

2 files changed

+90
-18
lines changed

2 files changed

+90
-18
lines changed

src/Decimal.php

Lines changed: 26 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
namespace Litipk\BigNumbers;
44

5+
use Litipk\BigNumbers\DecimalConstants as DecimalConstants;
56
use Litipk\BigNumbers\InfiniteDecimal as InfiniteDecimal;
67

78
use Litipk\Exceptions\NotImplementedException as NotImplementedException;
@@ -66,8 +67,9 @@ public static function getNegativeInfinite()
6667
/**
6768
* Decimal "constructor".
6869
*
69-
* @param mixed $value
70-
* @param integer $scale
70+
* @param mixed $value
71+
* @param integer $scale
72+
* @return Decimal
7173
*/
7274
public static function create($value, $scale = null)
7375
{
@@ -286,7 +288,7 @@ public function mul(Decimal $b, $scale = null)
286288
if ($b->isInfinite()) {
287289
return $b->mul($this);
288290
} elseif ($b->isZero()) {
289-
return Decimal::fromInteger(0, $scale);
291+
return DecimalConstants::Zero();
290292
}
291293

292294
return self::fromString(
@@ -311,10 +313,8 @@ public function div(Decimal $b, $scale = null)
311313

312314
if ($b->isZero()) {
313315
throw new \DomainException("Division by zero is not allowed.");
314-
} elseif ($this->isZero()) {
315-
return self::fromDecimal($this, $scale);
316-
} elseif ($b->isInfinite()) {
317-
return Decimal::fromInteger(0, $scale);
316+
} elseif ($this->isZero() || $b->isInfinite()) {
317+
return DecimalConstants::Zero();
318318
} else {
319319
if ($scale !== null) {
320320
$divscale = $scale;
@@ -356,7 +356,7 @@ public function sqrt($scale = null)
356356
"Decimal can't handle square roots of negative numbers (it's only for real numbers)."
357357
);
358358
} elseif ($this->isZero()) {
359-
return Decimal::fromDecimal($this, $scale);
359+
return DecimalConstants::Zero();
360360
}
361361

362362
$sqrt_scale = ($scale !== null ? $scale : $this->scale);
@@ -385,7 +385,7 @@ public function pow(Decimal $b, $scale = null)
385385
);
386386
}
387387
} elseif ($b->isZero()) {
388-
return Decimal::fromInteger(1, $scale);
388+
return DecimalConstants::One();
389389
} elseif ($b->scale == 0) {
390390
$pow_scale = $scale === null ?
391391
max($this->scale, $b->scale) : max($this->scale, $b->scale, $scale);
@@ -445,6 +445,7 @@ public function log10($scale = null)
445445
}
446446

447447
/**
448+
* @param integer $scale
448449
* @return boolean
449450
*/
450451
public function isZero($scale = null)
@@ -470,6 +471,14 @@ public function isNegative()
470471
return ($this->value[0] === '-');
471472
}
472473

474+
/**
475+
* @return boolean
476+
*/
477+
public function isInteger()
478+
{
479+
return (preg_match('/^[+\-]?[0-9]+(\.0+)?$/', $this->value, $captures) === 1);
480+
}
481+
473482
/**
474483
* @return boolean
475484
*/
@@ -509,6 +518,7 @@ public function equals(Decimal $b, $scale = null)
509518
* $this > $b : returns 1 , $this < $b : returns -1 , $this == $b : returns 0
510519
*
511520
* @param Decimal $b
521+
* @param integer $scale
512522
* @return integer
513523
*/
514524
public function comp(Decimal $b, $scale = null)
@@ -661,9 +671,9 @@ public function sin($scale = null) {
661671

662672
// Next use Maclaurin's theorem to approximate sin with high enough accuracy
663673
// note that the accuracy is depended on the accuracy of the given PI constant
664-
$faculty = Decimal::fromString("1"); // Calculates the faculty under the sign
665-
$xPowerN = Decimal::fromString("1"); // Calculates x^n
666-
$approx = Decimal::fromString("0"); // keeps track of our approximation for sin(x)
674+
$faculty = DecimalConstants::One(); // Calculates the faculty under the sign
675+
$xPowerN = DecimalConstants::One(); // Calculates x^n
676+
$approx = DecimalConstants::Zero(); // keeps track of our approximation for sin(x)
667677

668678
$change = InfiniteDecimal::getPositiveInfinite();
669679

@@ -706,9 +716,9 @@ public function cos($scale = null) {
706716

707717
// Next use Maclaurin's theorem to approximate sin with high enough accuracy
708718
// note that the accuracy is depended on the accuracy of the given PI constant
709-
$faculty = Decimal::fromString("1"); // Calculates the faculty under the sign
710-
$xPowerN = Decimal::fromString("1"); // Calculates x^n
711-
$approx = Decimal::fromString("1"); // keeps track of our approximation for sin(x)
719+
$faculty = DecimalConstants::One(); // Calculates the faculty under the sign
720+
$xPowerN = DecimalConstants::One(); // Calculates x^n
721+
$approx = DecimalConstants::One(); // keeps track of our approximation for sin(x)
712722

713723
$change = InfiniteDecimal::getPositiveInfinite();
714724

@@ -980,10 +990,8 @@ private static function normalizeSign($sign)
980990
*/
981991
private static function countSignificativeDigits(Decimal $val, Decimal $abs)
982992
{
983-
$one = Decimal::fromInteger(1);
984-
985993
return strlen($val->value) - (
986-
($abs->comp($one) === -1) ? 2 : max($val->scale, 1)
994+
($abs->comp(DecimalConstants::One()) === -1) ? 2 : max($val->scale, 1)
987995
) - ($val->isNegative() ? 1 : 0);
988996
}
989997
}
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
<?php
2+
3+
use Litipk\BigNumbers\Decimal as Decimal;
4+
5+
6+
date_default_timezone_set('UTC');
7+
8+
9+
class DecimalIsIntegerTest extends PHPUnit_Framework_TestCase
10+
{
11+
public function testIntegers()
12+
{
13+
$this->assertTrue(Decimal::fromInteger(-200)->isInteger());
14+
$this->assertTrue(Decimal::fromInteger(-2)->isInteger());
15+
$this->assertTrue(Decimal::fromInteger(-1)->isInteger());
16+
$this->assertTrue(Decimal::fromInteger(0)->isInteger());
17+
$this->assertTrue(Decimal::fromInteger(1)->isInteger());
18+
$this->assertTrue(Decimal::fromInteger(2)->isInteger());
19+
$this->assertTrue(Decimal::fromInteger(200)->isInteger());
20+
21+
$this->assertTrue(Decimal::fromString("-200")->isInteger());
22+
$this->assertTrue(Decimal::fromString("-2")->isInteger());
23+
$this->assertTrue(Decimal::fromString("-1")->isInteger());
24+
$this->assertTrue(Decimal::fromString("0")->isInteger());
25+
$this->assertTrue(Decimal::fromString("1")->isInteger());
26+
$this->assertTrue(Decimal::fromString("2")->isInteger());
27+
$this->assertTrue(Decimal::fromString("200")->isInteger());
28+
29+
$this->assertTrue(Decimal::fromString("-200.000")->isInteger());
30+
$this->assertTrue(Decimal::fromString("-2.000")->isInteger());
31+
$this->assertTrue(Decimal::fromString("-1.000")->isInteger());
32+
$this->assertTrue(Decimal::fromString("0.000")->isInteger());
33+
$this->assertTrue(Decimal::fromString("1.000")->isInteger());
34+
$this->assertTrue(Decimal::fromString("2.000")->isInteger());
35+
$this->assertTrue(Decimal::fromString("200.000")->isInteger());
36+
37+
$this->assertTrue(Decimal::fromFloat(-200.0)->isInteger());
38+
$this->assertTrue(Decimal::fromFloat(-2.0)->isInteger());
39+
$this->assertTrue(Decimal::fromFloat(-1.0)->isInteger());
40+
$this->assertTrue(Decimal::fromFloat(0.0)->isInteger());
41+
$this->assertTrue(Decimal::fromFloat(1.0)->isInteger());
42+
$this->assertTrue(Decimal::fromFloat(2.0)->isInteger());
43+
$this->assertTrue(Decimal::fromFloat(200.0)->isInteger());
44+
}
45+
46+
public function testNotIntegers()
47+
{
48+
$this->assertFalse(Decimal::fromString("-200.001")->isInteger());
49+
$this->assertFalse(Decimal::fromString("-2.001")->isInteger());
50+
$this->assertFalse(Decimal::fromString("-1.001")->isInteger());
51+
$this->assertFalse(Decimal::fromString("0.001")->isInteger());
52+
$this->assertFalse(Decimal::fromString("1.001")->isInteger());
53+
$this->assertFalse(Decimal::fromString("2.001")->isInteger());
54+
$this->assertFalse(Decimal::fromString("200.001")->isInteger());
55+
56+
$this->assertFalse(Decimal::fromFloat(-200.001)->isInteger());
57+
$this->assertFalse(Decimal::fromFloat(-2.001)->isInteger());
58+
$this->assertFalse(Decimal::fromFloat(-1.001)->isInteger());
59+
$this->assertFalse(Decimal::fromFloat(0.001)->isInteger());
60+
$this->assertFalse(Decimal::fromFloat(1.001)->isInteger());
61+
$this->assertFalse(Decimal::fromFloat(2.001)->isInteger());
62+
$this->assertFalse(Decimal::fromFloat(200.001)->isInteger());
63+
}
64+
}

0 commit comments

Comments
 (0)