Skip to content

Instantly share code, notes, and snippets.

@d4rkne55
Last active September 21, 2019 19:33
Show Gist options
  • Save d4rkne55/2506f771b88fe1f7c12718541244fdde to your computer and use it in GitHub Desktop.
Save d4rkne55/2506f771b88fe1f7c12718541244fdde to your computer and use it in GitHub Desktop.
Class for getting the spelled out string of a number (was a coding challenge once)
<?php
class NumberSpell
{
public $number;
public $spelled;
private $rules = array(
0 => array('one', 'two', 'three', 'four', 'five', 'six', 'seven', 'eight', 'nine'),
1 => array(null, 'twen', 'thir', 'for', 'fif', null, null, null, null)
);
private $exceptions = array(
10 => 'ten',
11 => 'eleven',
12 => 'twelve',
14 => 'fourteen'
);
public function __construct($number) {
if (is_float($number) || (!is_int($number) && !is_numeric($number))) {
throw new InvalidArgumentException('Only integers or strings with an integer supported.');
}
$this->number = (int) $number;
$spellData = $this->transformToSpell($number);
$this->spelled = implode(' ', array_reverse(array_filter($spellData)));
}
public function transformToSpell($number) {
if (isset($this->exceptions[$number])) {
return array($this->exceptions[$number]);
}
$digits = str_split(strrev((string) $number));
$spelledDigits = array();
foreach ($digits as $pos => $digit) {
if ($pos == 0) {
if (!isset($digits[1]) || $digits[1] != 1) {
$spelledDigits[0] = ($digit > 0) ? $this->getSpelling($digit, $pos) : '';
}
} elseif ($pos == 1) {
if (isset($this->exceptions[$digit . $digits[0]])) {
$spelledDigits[1] = $this->exceptions[$digit . $digits[0]];
continue;
}
$digitContext = ($digit == 1) ? $digits[0] : $digit;
if ($digit > 0) {
$spelledDigits[1] = rtrim($this->getSpelling($digitContext, $pos), 't');
$spelledDigits[1] .= ($digit == 1) ? 'teen' : 'ty';
}
} elseif ($pos > 1 && $digit > 0) {
$spelledDigits[$pos] = $this->getSpelling($digit, 0);
$spelledDigits[$pos] .= ($pos == 2) ? ' hundred' : ' thousand';
}
}
return $spelledDigits;
}
private function getSpelling($value, $pos) {
if ($value > 9 || $value < 1) {
return false;
}
$value--;
if (isset($this->rules[$pos][$value]) && $this->rules[$pos][$value] != null) {
return $this->rules[$pos][$value];
} else {
return $this->rules[0][$value];
}
}
public function __toString() {
return $this->spelled;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment