Skip to content

Commit 5087733

Browse files
authored
multiply by zero is always zero
1 parent 39e5e0c commit 5087733

File tree

2 files changed

+58
-0
lines changed

2 files changed

+58
-0
lines changed

src/Analyser/MutatingScope.php

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1040,6 +1040,34 @@ private function resolveType(Expr $node): Type
10401040
return new StringType();
10411041
}
10421042

1043+
if (
1044+
$node instanceof Node\Expr\BinaryOp\Mul
1045+
|| $node instanceof Node\Expr\AssignOp\Mul
1046+
) {
1047+
if ($node instanceof Node\Expr\AssignOp) {
1048+
$leftType = $this->getType($node->var)->toNumber();
1049+
$rightType = $this->getType($node->expr)->toNumber();
1050+
} else {
1051+
$leftType = $this->getType($node->left)->toNumber();
1052+
$rightType = $this->getType($node->right)->toNumber();
1053+
}
1054+
1055+
$floatType = new FloatType();
1056+
1057+
if ($leftType instanceof ConstantIntegerType && $leftType->getValue() === 0) {
1058+
if ($floatType->isSuperTypeOf($rightType)->yes()) {
1059+
return new ConstantFloatType(0.0);
1060+
}
1061+
return new ConstantIntegerType(0);
1062+
}
1063+
if ($rightType instanceof ConstantIntegerType && $rightType->getValue() === 0) {
1064+
if ($floatType->isSuperTypeOf($leftType)->yes()) {
1065+
return new ConstantFloatType(0.0);
1066+
}
1067+
return new ConstantIntegerType(0);
1068+
}
1069+
}
1070+
10431071
if (
10441072
$node instanceof Node\Expr\BinaryOp\Div
10451073
|| $node instanceof Node\Expr\AssignOp\Div

tests/PHPStan/Analyser/data/math.php

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,4 +109,34 @@ public function doSit(int $i, int $j): void
109109
assertType('int', $i - $j);
110110
}
111111

112+
/**
113+
* @param int<-5, 5> $range
114+
*/
115+
public function multiplyZero(int $i, float $f, $range): void
116+
{
117+
assertType('0', $i * false);
118+
assertType('0.0', $f * false);
119+
assertType('0', $range * false);
120+
121+
assertType('0', $i * '0');
122+
assertType('0.0', $f * '0');
123+
assertType('0', $range * '0');
124+
125+
assertType('0', $i * 0);
126+
assertType('0.0', $f * 0);
127+
assertType('0', $range * 0);
128+
129+
assertType('0', 0 * $i);
130+
assertType('0.0', 0 * $f);
131+
assertType('0', 0 * $range);
132+
133+
$i *= 0;
134+
$f *= 0;
135+
$range *= 0;
136+
assertType('0', $i);
137+
assertType('0.0', $f);
138+
assertType('0', $range);
139+
140+
}
141+
112142
}

0 commit comments

Comments
 (0)