Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.
Common duplication problems, and corresponding solutions are:
| 1 | <?php |
||
| 7 | class HTMLPurifier_UnitConverter |
||
|
|
|||
| 8 | { |
||
| 9 | |||
| 10 | const ENGLISH = 1; |
||
| 11 | const METRIC = 2; |
||
| 12 | const DIGITAL = 3; |
||
| 13 | |||
| 14 | /** |
||
| 15 | * Units information array. Units are grouped into measuring systems |
||
| 16 | * (English, Metric), and are assigned an integer representing |
||
| 17 | * the conversion factor between that unit and the smallest unit in |
||
| 18 | * the system. Numeric indexes are actually magical constants that |
||
| 19 | * encode conversion data from one system to the next, with a O(n^2) |
||
| 20 | * constraint on memory (this is generally not a problem, since |
||
| 21 | * the number of measuring systems is small.) |
||
| 22 | */ |
||
| 23 | protected static $units = array( |
||
| 24 | self::ENGLISH => array( |
||
| 25 | 'px' => 3, // This is as per CSS 2.1 and Firefox. Your mileage may vary |
||
| 26 | 'pt' => 4, |
||
| 27 | 'pc' => 48, |
||
| 28 | 'in' => 288, |
||
| 29 | self::METRIC => array('pt', '0.352777778', 'mm'), |
||
| 30 | ), |
||
| 31 | self::METRIC => array( |
||
| 32 | 'mm' => 1, |
||
| 33 | 'cm' => 10, |
||
| 34 | self::ENGLISH => array('mm', '2.83464567', 'pt'), |
||
| 35 | ), |
||
| 36 | ); |
||
| 37 | |||
| 38 | /** |
||
| 39 | * Minimum bcmath precision for output. |
||
| 40 | * @type int |
||
| 41 | */ |
||
| 42 | protected $outputPrecision; |
||
| 43 | |||
| 44 | /** |
||
| 45 | * Bcmath precision for internal calculations. |
||
| 46 | * @type int |
||
| 47 | */ |
||
| 48 | protected $internalPrecision; |
||
| 49 | |||
| 50 | /** |
||
| 51 | * Whether or not BCMath is available. |
||
| 52 | * @type bool |
||
| 53 | */ |
||
| 54 | private $bcmath; |
||
| 55 | |||
| 56 | public function __construct($output_precision = 4, $internal_precision = 10, $force_no_bcmath = false) |
||
| 62 | |||
| 63 | /** |
||
| 64 | * Converts a length object of one unit into another unit. |
||
| 65 | * @param HTMLPurifier_Length $length |
||
| 66 | * Instance of HTMLPurifier_Length to convert. You must validate() |
||
| 67 | * it before passing it here! |
||
| 68 | * @param string $to_unit |
||
| 69 | * Unit to convert to. |
||
| 70 | * @return HTMLPurifier_Length|bool |
||
| 71 | * @note |
||
| 72 | * About precision: This conversion function pays very special |
||
| 73 | * attention to the incoming precision of values and attempts |
||
| 74 | * to maintain a number of significant figure. Results are |
||
| 75 | * fairly accurate up to nine digits. Some caveats: |
||
| 76 | * - If a number is zero-padded as a result of this significant |
||
| 77 | * figure tracking, the zeroes will be eliminated. |
||
| 78 | * - If a number contains less than four sigfigs ($outputPrecision) |
||
| 79 | * and this causes some decimals to be excluded, those |
||
| 80 | * decimals will be added on. |
||
| 81 | */ |
||
| 82 | public function convert($length, $to_unit) |
||
| 186 | |||
| 187 | /** |
||
| 188 | * Returns the number of significant figures in a string number. |
||
| 189 | * @param string $n Decimal number |
||
| 190 | * @return int number of sigfigs |
||
| 191 | */ |
||
| 192 | public function getSigFigs($n) |
||
| 206 | |||
| 207 | /** |
||
| 208 | * Adds two numbers, using arbitrary precision when available. |
||
| 209 | * @param string $s1 |
||
| 210 | * @param string $s2 |
||
| 211 | * @param int $scale |
||
| 212 | * @return string |
||
| 213 | */ |
||
| 214 | View Code Duplication | private function add($s1, $s2, $scale) |
|
| 222 | |||
| 223 | /** |
||
| 224 | * Multiples two numbers, using arbitrary precision when available. |
||
| 225 | * @param string $s1 |
||
| 226 | * @param string $s2 |
||
| 227 | * @param int $scale |
||
| 228 | * @return string |
||
| 229 | */ |
||
| 230 | View Code Duplication | private function mul($s1, $s2, $scale) |
|
| 238 | |||
| 239 | /** |
||
| 240 | * Divides two numbers, using arbitrary precision when available. |
||
| 241 | * @param string $s1 |
||
| 242 | * @param string $s2 |
||
| 243 | * @param int $scale |
||
| 244 | * @return string |
||
| 245 | */ |
||
| 246 | View Code Duplication | private function div($s1, $s2, $scale) |
|
| 254 | |||
| 255 | /** |
||
| 256 | * Rounds a number according to the number of sigfigs it should have, |
||
| 257 | * using arbitrary precision when available. |
||
| 258 | * @param float $n |
||
| 259 | * @param int $sigfigs |
||
| 260 | * @return string |
||
| 261 | */ |
||
| 262 | private function round($n, $sigfigs) |
||
| 282 | |||
| 283 | /** |
||
| 284 | * Scales a float to $scale digits right of decimal point, like BCMath. |
||
| 285 | * @param float $r |
||
| 286 | * @param int $scale |
||
| 287 | * @return string |
||
| 288 | */ |
||
| 289 | private function scale($r, $scale) |
||
| 305 | } |
||
| 306 | |||
| 308 |
You can fix this by adding a namespace to your class:
When choosing a vendor namespace, try to pick something that is not too generic to avoid conflicts with other libraries.