extension Int { private static let bigNames = [ 1_000: "thousand", 1_000_000: "million", 1_000_000_000: "billion", 1_000_000_000_000: "trillion", 1_000_000_000_000_000: "quadrillion", 1_000_000_000_000_000_000: "quintillion" ] private static let names = [ 1: "one", 2: "two", 3: "three", 4: "four", 5: "five", 6: "six", 7: "seven", 8: "eight", 9: "nine", 10: "ten", 11: "eleven", 12: "twelve", 13: "thirteen", 14: "fourteen", 15: "fifteen", 16: "sixteen", 17: "seventeen", 18: "eighteen", 19: "nineteen", 20: "twenty", 30: "thirty", 40: "forty", 50: "fifty", 60: "sixty", 70: "seventy", 80: "eighty", 90: "ninety" ] public var numberName: String { guard self != 0 else { return "zero" } let neg = self < 0 let maxNeg = self == Int.min var nn: Int if maxNeg { nn = -(self + 1) } else if neg { nn = -self } else { nn = self } var digits3 = [Int](repeating: 0, count: 7) for i in 0..<7 { digits3[i] = (nn % 1000) nn /= 1000 } func threeDigitsToText(n: Int) -> String { guard n != 0 else { return "" } var ret = "" let hundreds = n / 100 let remainder = n % 100 if hundreds > 0 { ret += "\(Int.names[hundreds]!) hundred" if remainder > 0 { ret += " " } } if remainder > 0 { let tens = remainder / 10 let units = remainder % 10 if tens > 1 { ret += Int.names[tens * 10]! if units > 0 { ret += "-\(Int.names[units]!)" } } else { ret += Int.names[remainder]! } } return ret } let strings = (0..<7).map({ threeDigitsToText(n: digits3[$0]) }) var name = strings[0] var big = 1000 for i in 1...6 { if digits3[i] > 0 { var name2 = "\(strings[i]) \(Int.bigNames[big]!)" if name.count > 0 { name2 += ", " } name = name2 + name } big &*= 1000 } if maxNeg { name = String(name.dropLast(5) + "eight") } return neg ? "minus \(name)" : name } } let nums = [ 0, 1, 7, 10, 18, 22, 67, 99, 100, 105, 999, -1056, 1000005000, 2074000000, 1234000000745003, Int.min ] for number in nums { print("\(number) => \(number.numberName)") }