从字符串中提取货币和价格值

时间:2015-08-21 20:07:39

标签: ios objective-c swift

我正试图找到一种从字符串中提取货币和价格值的好方法。它应该适用于多种货币。部分......

  • 提取数字 - 可以是int或decimal值
  • 检测附近的货币符号,使其与货币代码相匹配
  • 忽略不是价格的数字 - 例如没有附加到货币指标

实施例

  • “苹果,2x橙子和草莓5.0欧元”
  • “苹果,32个橙子和草莓5.0€”
  • “苹果,橘子5€和草莓”
  • “苹果,橘子和草莓,价格为5欧元”

结果

  • 价格为:5.0
  • 货币代码和符号:€(EUR)

另一个例子

  • “苹果,32种橙子和草莓,5.0美元”→数量:5.0,货币美元(美元)

采用不同货币的方法有什么好办法?

2 个答案:

答案 0 :(得分:2)

您可以使用正则表达式。我在我的框架中使用以下内容:

class Regex {
  private let internalExpression: NSRegularExpression
  let pattern: String
  var groups:[String]? = nil

  init(_ pattern: String) {
    self.pattern = pattern
    let regex: NSRegularExpression?
    do {
      regex = try NSRegularExpression(pattern: pattern, options: .CaseInsensitive)
    } catch let error as NSError {
      fatalError("Invalid pattern '\(pattern)` (\(error))")
    }
    internalExpression = regex!
  }

  init(_ pattern: String, options: NSRegularExpressionOptions) {
    self.pattern = pattern
    let regex: NSRegularExpression?
    do {
      regex = try NSRegularExpression(pattern: pattern, options: options)
    } catch let error as NSError {
      fatalError("Invalid pattern '\(pattern)` (\(error))")
    }
    internalExpression = regex!
  }

  func test(input: String) -> Bool {
    let matches = self.internalExpression.matchesInString(input, options: [], range:NSMakeRange(0, input.characters.count)) as [NSTextCheckingResult]
    if matches.count == 0 { groups = nil; return false }
    if internalExpression.numberOfCaptureGroups > 0 {
      groups = [String]()
      let match = matches[0] as NSTextCheckingResult
      for index in 1..<match.numberOfRanges {
        let range = match.rangeAtIndex(index)
        if range.location == 9223372036854775807 { groups!.append("") }
        else { groups!.append((input as NSString).substringWithRange(range)) }
      }
    }
    return true
  }

  func match(index:Int) -> String? {
    return groups![index]
  }
}

然后你可以检查

let regexEuro = Regex("(\\d+(\\.\\d+)?) *€")
let regexDollar = Regex("\\$ *(\\d+(\\.\\d+)?)")
if regexEuro.test("This is 20 € ...") {
  print(regexEuro.match(0))
}
if regexDollar.test("This is $ 20.3 ...") {
  print(regexDollar.match(0))
}

答案 1 :(得分:0)

Thomas发布的上述Regex框架已更新为Swift 4

class Regex {
    private let regex: NSRegularExpression
    let pattern: String
    var groups: [String] = []
    init(_ pattern: String, options: NSRegularExpression.Options = []) throws {
        self.pattern = pattern
        regex = try NSRegularExpression(pattern: pattern, options: options)
    }
    func contains(string: String) -> Bool {
        groups = []
        let matches = regex.matches(in: string, options: [], range: NSMakeRange(0, string.utf16.count)) as [NSTextCheckingResult]
        guard !matches.isEmpty else {
            return false
        }
        if regex.numberOfCaptureGroups > 0,
        let firstMatch = matches.first {
            for index in 1..<firstMatch.numberOfRanges {
                let range = firstMatch.range(at: index)
                if range.location == .max {
                    groups.append("")
                } else {
                    groups.append((string as NSString).substring(with: range))
                }
            }
        }
        return true
    }
    func match(index: Int) -> String? {
        return groups[index]
    }
}

let regexEuro = try! Regex("(\\d+(\\.\\d+)?) *€")
let regexDollar = try! Regex("\\$ *(\\d+(\\.\\d+)?)")
if regexEuro.contains(string: "This costs 20€"),
    let value = regexEuro.match(index: 0) {
    print("Euro value:", value)  // "20\n"
}

if regexDollar.contains(string: "This costs $20.3"),
    let value = regexDollar.match(index: 0) {
    print("Dolar value:", value)  // "20.3\n"
}