-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathmathematical_operator.php
More file actions
119 lines (103 loc) · 3.35 KB
/
Copy pathmathematical_operator.php
File metadata and controls
119 lines (103 loc) · 3.35 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
<?php
declare(strict_types=1);
namespace Zlikavac32\ZEnum\Examples;
use LogicException;
use Zlikavac32\ZEnum\ZEnum;
require_once __DIR__ . '/../vendor/autoload.php';
/**
* Main benefit of this enum concept is chance to use polymorphism. It's possible to define enum class with abstract
* methods or with a constructor. Let's explore this example with some mathematical operators that should have
* polymorphic behaviour.
*
* We will define four enums and we will provide operations for every enum that exists. To achieve that in our named
* enum class we define abstract public function apply(float $left, float $right): float; method and then implement in
* each anonymous class the required behaviour
*/
/**
* @method static MathematicalOperator PLUS
* @method static MathematicalOperator MINUS
* @method static MathematicalOperator TIMES
* @method static MathematicalOperator DIV
*/
abstract class MathematicalOperator extends ZEnum
{
protected static function enumerate(): array
{
return [
'PLUS' => new class extends MathematicalOperator
{
public function apply(float $left, float $right): float
{
return $left + $right;
}
public function __toString(): string
{
return '+';
}
},
'MINUS' => new class extends MathematicalOperator
{
public function apply(float $left, float $right): float
{
return $left - $right;
}
public function __toString(): string
{
return '-';
}
},
'TIMES' => new class extends MathematicalOperator
{
public function apply(float $left, float $right): float
{
return $left * $right;
}
public function __toString(): string
{
return '*';
}
},
'DIV' => new class extends MathematicalOperator
{
public function apply(float $left, float $right): float
{
if (.0 === $right) {
throw new LogicException('Division by zero');
}
return $left / $right;
}
public function __toString(): string
{
return '/';
}
},
];
}
abstract public function apply(float $left, float $right): float;
}
//Let PLUS enum apply its operation
var_dump(
MathematicalOperator::PLUS()
->apply(10, 20)
); // double(30)
//We can iterate over every operator and let him apply its operation. We also override __toString() method
foreach (MathematicalOperator::iterator() as $operator) {
$left = 10;
$right = 20;
var_dump(
sprintf(
'%.2lf %s %.2lf = %.2lf',
$left,
(string) $operator,
$right,
$operator->apply(
$left,
$right
)
)
);
}
// string(21) "10.00 + 20.00 = 30.00"
// string(22) "10.00 - 20.00 = -10.00"
// string(22) "10.00 * 20.00 = 200.00"
// string(20) "10.00 / 20.00 = 0.50"