你好,我的朋友,我需要你的帮助! :)我是斯威夫特的绝对初学者,完全不知道我在做什么。
我需要从我转换成字符串的txt文件中提取所有数字。我想将所有数字保存到一个新的数组中,我还必须使用CharacterView来解决问题。
这是我到目前为止所得到的。从txt文件中读取没有问题。
func readFile(){
let path = Bundle.main.path(forResource: "paragraph", ofType: "txt")
var fileContents : String? = nil
do {
fileContents = try String(contentsOfFile: path!, encoding: String.Encoding.utf8)
} catch _ as NSError {
//ERROR HANDLING
}
print(fileContents)
}
这是文件:
Lorem存有消费者§9(1)胡萝卜,consetetur sadipscing多年来,但是远投nonumy矿石等疼痛最令人兴奋的。 (2)项目的床直径。 55但是,他们中的真理两个,公正,感到痛苦和东西预览。在维罗EOS。 (3)上述1,疼痛是最令人兴奋,但该项目的直径。不过,说实话,两分钟,只是,和感觉,以及东西预览。 LOREM。
感谢您的时间!
这是一个简单的方法,不幸的是它不使用CharacterView
,因为这会使它复杂化:
func readFile(){
// Make sure getting the path and reading the file succeeds
guard
let path = Bundle.main.path(forResource: "paragraph", ofType: "txt"),
let fileContents = try? String(contentsOfFile: path, encoding: String.Encoding.utf8)
else { return }
// split string into substrings that only contain numbers
let substrings = fileContents.components(separatedBy: CharacterSet.decimalDigits.inverted)
// flatMap performs action on each substring
// and only returns non-nil values,
// thus returns [Int]
let numbers = substrings.flatMap {
// convert each substring into an Int?
return Int($0)
}
print(numbers)
}
因为Int
的初始化程序需要String
,所以不需要使用CharacterView
。一旦文本中的数字从非数字中分割出来,就可以直接从String
转换为Int
。使用CharacterView
将是一个不必要的中间人。但是,您可以编写自己的Int
init?(String)
版本,该版本使用CharacterView
来构建值。
import Foundation
extension String {
func onlyNumbers() -> [NSNumber] {
let formatter = NumberFormatter()
formatter.numberStyle = .decimal
let charset = CharacterSet.init(charactersIn: " ,")
return matches(for: "[+-]?([0-9]+([., ][0-9]*)*|[.][0-9]+)").compactMap { string in
return formatter.number(from: string.trimmingCharacters(in: charset))
}
}
// https://stackoverflow.com/a/54900097/4488252
func matches(for regex: String) -> [String] {
guard let regex = try? NSRegularExpression(pattern: regex, options: [.caseInsensitive]) else { return [] }
let matches = regex.matches(in: self, options: [], range: NSMakeRange(0, self.count))
return matches.compactMap { match in
guard let range = Range(match.range, in: self) else { return nil }
return String(self[range])
}
}
}
let text = "dasdxcw 12345678 eadwd 333.222 reqw 3 333 444.22, sfsa 44. qewqwdsaw qe aw, 0.123456678 and .23 asdasdas 32,322,222,444.8"
print("Original text: \(text)")
print("Only numbers: \(text.onlyNumbers())")
//Original text: dasdxcw 12345678 eadwd 333.222 reqw 3 333 444.22, sfsa 44. qewqwdsaw qe aw, 0.123456678 and .23 asdasdas 32,322,222,444.8
//Only numbers: [12345678, 333.222, 3333444.22, 44, 0.123456678, 0.23, 32322222444.8]