1 | <?php |
||
24 | class BaseConverter implements Converter |
||
25 | { |
||
26 | /** @var Converter Selected converter for base conversion */ |
||
27 | private $converter; |
||
28 | |||
29 | /** @var int Precision provided to the fraction converter */ |
||
30 | private $precision; |
||
31 | |||
32 | /** @var NumberBase Number base used by provided numbers */ |
||
33 | private $source; |
||
34 | |||
35 | /** @var NumberBase Number base used by returned numbers */ |
||
36 | private $target; |
||
37 | |||
38 | /** |
||
39 | * Creates a new instance of BaseConverter. |
||
40 | * |
||
41 | * The source and target number bases can be provided either as an instance |
||
42 | * of the NumberBase class or as constructor arguments that are provided to |
||
43 | * the NumberBase class. |
||
44 | * |
||
45 | * The constructor will select the most optimal conversion strategy based |
||
46 | * on the provided number bases. |
||
47 | * |
||
48 | * @see NumberBase::__construct |
||
49 | * @param mixed $sourceBase Number base used by the provided numbers |
||
50 | * @param mixed $targetBase Number base used by the returned numbers |
||
51 | */ |
||
52 | 39 | public function __construct($sourceBase, $targetBase) |
|
65 | |||
66 | /** |
||
67 | * Converts the provided number from base to another. |
||
68 | * |
||
69 | * This method provides a convenient replacement to PHP's built in |
||
70 | * `base_convert()`. The number bases are simply passed along to the |
||
71 | * constructor, which means they can be instances of NumberBase class or |
||
72 | * constructor parameters for that class. |
||
73 | * |
||
74 | * Note that due to the way the constructor parameters for NumberBase work, |
||
75 | * this method can be used exactly the same way as `base_convert()`. |
||
76 | * |
||
77 | * @param string $number The number to convert |
||
78 | * @param mixed $fromBase Number base used by the provided number |
||
79 | * @param mixed $toBase Number base used by the returned number |
||
80 | * @param int $precision Precision for inaccurate conversion |
||
81 | * @return string|false The converted number or false on error |
||
82 | */ |
||
83 | 3 | public static function baseConvert($number, $fromBase, $toBase, $precision = -1) |
|
90 | |||
91 | /** |
||
92 | * Converts the number provided as a string from source base to target base. |
||
93 | * |
||
94 | * This method provides convenient conversions by accepting the number as |
||
95 | * a string. The number may optionally be preceded by a plus or minus sign |
||
96 | * which is prepended to the result as well. The number may also have a |
||
97 | * period, which separates the integer part and the fractional part. |
||
98 | * |
||
99 | * Due to the special meaning of `+`, `-` and `.`, it is not recommended to |
||
100 | * use this method to convert numbers when using number bases that have a |
||
101 | * meaning for these characters (such as base64). |
||
102 | * |
||
103 | * If the number contains invalid characters, the method will return false |
||
104 | * instead. |
||
105 | * |
||
106 | * @param string $number The number to convert |
||
107 | * @return string|false The converted number or false on error |
||
108 | */ |
||
109 | 18 | public function convert($number) |
|
110 | { |
||
111 | 18 | $integer = (string) $number; |
|
112 | 18 | $fractions = null; |
|
113 | 18 | $sign = ''; |
|
114 | |||
115 | 18 | if (in_array(substr($integer, 0, 1), ['+', '-'], true)) { |
|
116 | 12 | $sign = $integer[0]; |
|
117 | 12 | $integer = substr($integer, 1); |
|
118 | 4 | } |
|
119 | |||
120 | 18 | if (($pos = strpos($integer, '.')) !== false) { |
|
121 | 12 | $fractions = substr($integer, $pos + 1); |
|
122 | 12 | $integer = substr($integer, 0, $pos); |
|
123 | 4 | } |
|
124 | |||
125 | 18 | return $this->convertNumber($sign, $integer, $fractions); |
|
126 | } |
||
127 | |||
128 | /** |
||
129 | * Converts the different parts of the number and handles invalid digits. |
||
130 | * @param string $sign Sign that preceded the number or an empty string |
||
131 | * @param string $integer The integer part of the number |
||
132 | * @param string|null $fractions The fractional part of the number or null if none |
||
133 | * @return string|false The converted number or false on error |
||
134 | */ |
||
135 | 18 | private function convertNumber($sign, $integer, $fractions) |
|
136 | { |
||
137 | try { |
||
138 | 18 | $result = implode('', $this->convertInteger($this->source->splitString($integer))); |
|
139 | |||
140 | 15 | if ($fractions !== null) { |
|
141 | 14 | $result .= '.' . implode('', $this->convertFractions($this->source->splitString($fractions))); |
|
142 | 4 | } |
|
143 | 8 | } catch (DigitList\InvalidDigitException $ex) { |
|
144 | 3 | return false; |
|
145 | } |
||
146 | |||
147 | 15 | return $sign . $result; |
|
148 | } |
||
149 | |||
150 | 6 | public function setPrecision($precision) |
|
154 | |||
155 | 21 | public function convertInteger(array $number) |
|
159 | |||
160 | 18 | public function convertFractions(array $number) |
|
166 | } |
||
167 |