如何在Swift 4中将金字塔类型的字符串转换为双精度数组

3
我需要阅读下面提供的字符串,以便从该字符串中分离出由换行符分隔的双精度数组,因此每一行将成为一个不同的双精度数组。
var sampleString = """
                     55
                    94 48
                   95 30 96
                 77 71 26 67
                97 13 76 38 45
              07 36 79 16 37 68
             48 07 09 18 70 26 06
           18 72 79 46 59 79 29 90
          20 76 87 11 32 07 07 49 18
        27 83 58 35 71 11 25 57 29 85
       14 64 36 96 27 11 58 56 92 18 55
     02 90 03 60 48 49 41 46 33 36 47 23
    92 50 48 02 36 59 42 79 72 20 82 77 42
  56 78 38 80 39 75 02 71 66 66 01 03 55 72
 44 25 67 84 71 67 11 61 40 57 58 89 40 56 36
85 32 25 85 57 48 84 35 47 62 17 01 01 99 89 52
06 71 28 75 94 48 37 10 23 51 06 48 53 18 74 98 15
27 02 92 23 08 71 76 84 15 52 92 63 81 10 44 10 69 93
"""

例如:第一个数组=[55],第二个数组=[94, 48],以此类推。
我知道有类似的问题,我尝试使用字符串方法,如:replacingOccurrences(of:with:)、trimmingCharacters(in:)、split(separator:)等。首先,我尝试了以下内容:
let lineSeperatedString = sampleString.replacingOccurrences(of: "\n", with: ",")

    let whiteSpaceTrimmedString = lineSeperatedString.replacingOccurrences(of: "  ", with: "")

    print(whiteSpaceTrimmedString)

然后输出结果如下:
 55,94 48, 95 30 96, 77 71 26 67,97 13 76 38 45,07 36 79 16 37 68, 48 07 09 18 70 26 06, 18 72 79 46 59 79 29 90,20 76 87 11 32 07 07 49 18,27 83 58 35 71 11 25 57 29 85, 14 64 36 96 27 11 58 56 92 18 55, 02 90 03 60 48 49 41 46 33 36 47 23,92 50 48 02 36 59 42 79 72 20 82 77 42,56 78 38 80 39 75 02 71 66 66 01 03 55 72, 44 25 67 84 71 67 11 61 40 57 58 89 40 56 36, 85 32 25 85 57 48 84 35 47 62 17 01 01 99 89 52,06 71 28 75 94 48 37 10 23 51 06 48 53 18 74 98 15,27 02 92 23 08 71 76 84 15 52 92 63 81 10 44 10 69 93

离目标很近,如果忽略每个逗号分隔的部分开头的一些空格

然后我尝试了以下内容,以便可以将它们转换为Ints,但是失败了,并将每个数字转换为一个int本身;

let myUpdatedArray = whiteSpaceTrimmedString.split(separator: "\n")
    for i in myUpdatedArray {
        let temp = i.map{String($0)}
        for j in temp {
            if let myInt = Int(j) {
                print(myInt)
            }
        }

    }

抱歉,内容有点长,但我想展示我尝试过的所有方法,但是无法自行解决。

3个回答

6
您可以使用以下方法来将字符串分割成行:
  • components(separatedBy: .newlines)
您可以使用以下方法将每一行映射到外部数组:
  • map
您可以使用以下方法将每一行中的数字分开:
  • components(separatedBy: .whitespaces)
您可以使用以下方法将每一行中的数字转换为内部数组中的Double(忽略无效的浮点数):
  • compactMap(Double.init)
将它们整合起来:
import Foundation

var sampleString = """
55
94 48
95 30 96
"""

let values = sampleString.components(separatedBy: .newlines).map {
    $0.components(separatedBy: .whitespaces).compactMap(Double.init)
}

print(values) // [[55.0], [94.0, 48.0], [95.0, 30.0, 96.0]]

我使用了“split”基本上做了同样的事情:let pyr = sampleString.split(separator: "\n").map { $0.split(separator: " ").compactMap(Double.init) } - vacawama
非常感谢!很抱歉由于我的声望还不够高,我无法给您点赞,所以我想在这里向您表示感谢 :) - emrepun
@vacawama:你是对的,那也可以工作(因为Double.init接受一个SubSequence类型的参数)。而且它不需要Foundation框架。 - Martin R
@vacawama:你想把那个作为答案发布吗? - Martin R
@MartinR,我曾经犹豫过我的答案是否有足够的不同之处,但最终决定它值得独立发帖。 - vacawama

3

您可以使用一行代码来实现这个功能,使用split将字符串分成多行,使用map处理每一行,再次使用split将每一行分成单独的字符串,并使用compactMapDouble.init将项目转换为Double

let pyramid = sampleString.split(separator: "\n").map { $0.split(separator: " ").compactMap(Double.init) }

这与@MartinR的答案非常相似,只是这是纯粹的Swift代码,避免了使用Foundation框架。


1
尝试这段代码:

let rows = sampleString.components(separatedBy: .newlines)
var finalArray = [[Double]]()

for row in rows {
    let array = row.components(separatedBy: .whitespaces).compactMap { Double($0) }
    finalArray.append(array)
}

print(finalArray)

如果您使用的是Swift 4.0或更低版本,请用flatMap替换compactMap

1
非常感谢!很抱歉由于我的声望还不够高,我不能给您点赞,所以我想在这里向您表示感谢 :) - emrepun

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接