swift - 枚举 swift 字符串时获取 "String.Index"

标签 swift string swift-string

目前我们迭代字符串如下:

let greeting = "Hello"
for (intIndex, char) in greeting.enumerated() {
    let currentIndex = greeting.index(greeting.startIndex, offsetBy: intIndex)
    let indexAfterCurrentIndex = greeting.index(after: currentIndex)
    print(greeting[indexAfterCurrentIndex...])
}

我觉得写下面的代码是多余的。

let currentIndex = greeting.index(greeting.startIndex, offsetBy: intIndex)

Is there other way to get directly "String.Index" while iterating?

像这样

let greeting = "Hello"
for (stringIndex, char) in greeting.enumeratedXXX() {
    let indexAfterCurrentIndex = greeting.index(after: stringIndex)
    print(greeting[indexAfterCurrentIndex...])
}

最佳答案

没有内置的功能。您可以将其包装在自定义迭代器中,但随后您只能将相同类型的计算封装在不同的地方,所以这不是答案:)

代码复杂度

但是,您可以提高当前代码的性能:

greeting.index(greeting.startIndex, offsetBy: intIndex)
  • 这将为每次循环迭代计算从 startIndex 到结果索引的索引。
  • 使用index(_:offsetBy:) 进行的索引计算实际上只是另一个循环本身,其中它+1 每个索引。没有O(1) 方法来“计算”索引;它是通过 O(n)
  • 中的循环找到的

所以你自己的外层循环是线性的,O(n) n 迭代,每个字符一个。

然后使用内部循环计算索引意味着有 1+2+3+4+5+6+...n = (n^2 + n)/2 迭代,其中n 是本例中的 intIndex

这意味着该算法的复杂度为 *handwaiving* roundabout O(n + n^2)。二次方部分有问题!

更好的方法

您可以将复杂度降低到每次迭代 2 个操作,或 O(2n)。只需将之前计算的索引保存在内存中并自己 +1,避免从头开始重新计算。

代码如下:

let greeting = "Hello"
var index = greeting.startIndex
for char in greeting {
    let indexAfterCurrentIndex = greeting.index(after: index)
    print(greeting[indexAfterCurrentIndex...])
    index = indexAfterCurrentIndex
}

这仍然不是一个简单的内置解决方案,但您也可以封装这个更高效的算法,然后就可以开始了!

extension String {
    func forEachCharacterWithIndex(iterator: (String.Index, Character) -> Void) {
        var currIndex = self.startIndex
        for char in self {
            iterator(currIndex, char)
            currIndex = self.index(after: currIndex)
        }
    }
}

let greeting = "Hello"
greeting.forEachCharacterWithIndex { (index, char) in
    let indexAfterCurrentIndex = greeting.index(after: index)
    print(greeting[indexAfterCurrentIndex...])
}

关于swift - 枚举 swift 字符串时获取 "String.Index",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56686820/

相关文章:

swift - 查找两次之间剩余的分钟数

java - 检查字符串中给定字符出现的次数

swift - 什么是 String.Encoding.unicode?

ios - 创建可读 JSON 字符串的最简单方法是什么?

c++ - Xcode 中下一次出现的区分大小写选择

ios - UIImage View 没有自动布局的整数高度,绘制的线条变得模糊

python - 如何在 Pandas 中创建新列?

c++ - 初始化无法从const char [3]转换为std::string *

Swift 用条件替换字符串的出现