Swift中的Failable Float to Int转换

时间:2016-07-24 20:19:32

标签: swift math swift2 integer-arithmetic

我正在尝试找到一种在Swift中将FloatDouble转换为Int的可靠方法。当出现溢出时,我遇到了问题。

我们来看下面的例子:

let double = 9223372036854775807.0 // This is 2^63 - 1 (aka Int.max on 64 bits architecture)

print("Int.max is         : \(Int.max)")
print(String(format: "double value is    : %f", double))
print(String(format: "Double(Int.max) is : %f", Double(Int.max)))

let int: Int
if (double >= Double(Int.max)) {
    print("Warning : double is too big for int !")
    int = Int.max
} else {
    int = Int(double)
}

打印哪些:

 Int.max is         : 9223372036854775807
 double value is    : 9223372036854775808.000000
 Double(Int.max) is : 9223372036854775808.000000
 Warning : double is too big for int !

这种方法非常麻烦。此外,您可能已经注意到我测试了double >= Double(Int.max)而不是double > Double(Int.max)。那是因为Double(Int.max)实际上等于Int.max + 1因为四舍五入。对于32位架构,我的代码可能必须不同。

还有另外一种方法吗?就像我可能错过的可用初始化程序或更好,可移植的方法来做到这一点?

1 个答案:

答案 0 :(得分:2)

您可以通过为Int创建自己的可用初始化程序来扩展Double

extension Int {
    init?(double: Double) {
        if double >= Double(Int.max) || double < Double(Int.min) || double.isNaN || double.isInfinite {
            return nil
        } else {
            self = Int(double)
        }
    }
}

if let i = Int(double: 17) {
    print(i)
} else {
    print("nil")
}

// It also handles NaN and Infinite
let nan = sqrt(-1.0)
let inf = 1e1000

Int(double: nan)   // nil
Int(double: inf)   // nil