【发布时间】:2016-07-04 05:55:38
【问题描述】:
我希望在 Swift 中使用 Integer 并将其转换为罗马数字 String。有什么想法吗?
【问题讨论】:
-
我能否请一些 cmets 了解为什么这个问题被否决?
标签: swift nsnumber swift-extensions
我希望在 Swift 中使用 Integer 并将其转换为罗马数字 String。有什么想法吗?
【问题讨论】:
标签: swift nsnumber swift-extensions
你可以在Int 上写一个扩展,类似于下面看到的。
请注意:对于小于一的数字,此代码将返回“”。虽然就罗马数字而言这可能没问题(零不存在),但您可能希望在自己的实现中以不同方式处理。
extension Int {
var romanNumeral: String {
var integerValue = self
var numeralString = ""
let mappingList: [(Int, String)] = [(1000, "M"), (900, "CM"), (500, "D"), (400, "CD"), (100, "C"), (90, "XC"), (50, "L"), (40, "XL"), (10, "X"), (9, "IX"), (5, "V"), (4, "IV"), (1, "I")]
for i in mappingList {
while (integerValue >= i.0) {
integerValue -= i.0
numeralString += i.1
}
}
return numeralString
}
}
感谢 Kenneth Bruno 对改进代码的一些建议。
【讨论】:
for i in mappingList where (integerValue >= i.0) { 并将所有 mappingList[i] 更改为 i 来简化该代码。我也会把它变成一个计算属性,它非常适合。对我来说似乎是一个很好的算法!
var romanNumeral: String {。然后你可以把它称为number.romanNumeral,就像一个普通的属性一样。哦,删除第 7 行和第 10 行,你不再需要它们了。
这是我的 int 到 roman 转换器的版本(没有嵌套循环):
extension Int {
func toRoman() -> String {
let conversionTable: [(intNumber: Int, romanNumber: String)] =
[(1000, "M"),
(900, "CM"),
(500, "D"),
(400, "CD"),
(100, "C"),
(90, "XC"),
(50, "L"),
(40, "XL"),
(10, "X"),
(9, "IX"),
(5, "V"),
(4, "IV"),
(1, "I")]
var roman = ""
var remainder = 0
for entry in conversionTable {
let quotient = (self - remainder) / entry.intNumber
remainder += quotient * entry.intNumber
roman += String(repeating: entry.romanNumber, count: quotient)
}
return roman
}
}
【讨论】:
这是您问题的解决方案,请检查此
func convertRomanToInt(strRoman : String) -> Int {
let arrData = strRoman.map { String($0) }
let dictRomanValue = ["I" : 1, "V" : 5, "X" : 10, "L" : 50, "C" : 100, "D" : 500, "M" : 1000]
var currentValue = 0
var preValue = 0
var ans = 0
for (_,obj) in arrData.enumerated().reversed() {
_ = dictRomanValue.map({ strName in
if obj == strName.key {
currentValue = strName.value
if currentValue < preValue && preValue > 0 {
ans = ans - preValue + (preValue - currentValue)
preValue = strName.value
}else{
preValue = strName.value
ans = ans + strName.value
}
}else{
ans
}
})
}
return ans
}
使用方法:很简单,你要调用这个函数
示例:convertRomanToInt(strRoman: "LVIII")
注意:它仅适用于您的号码
如果你得到更多的数字,请在“dictRomanValue”中添加更大的罗马值。
【讨论】:
这就是使用 for 循环和字典的方法。
func romanToInt(_ s: String) -> Int {
let numDict: [String: Int] = ["I": 1, "V": 5, "X": 10, "L": 50, "C": 100, "D": 500, "M": 1000]
let stringArray = Array(s)
var result: Int = 0
for index in 0..<stringArray.count {
for (k, v) in numDict {
if String(stringArray[index]) == k {
if (index + 1) < stringArray.count {
if k == String(stringArray[index + 1]) {
result += v
} else {
let nextValue = stringArray[index + 1]
for (nextK, nextV) in numDict {
if String(nextValue) == nextK {
if v < nextV {
result -= v
} else {
result += v
}
}
}
}
} else {
result += v
}
}
}
}
return result
}
【讨论】: