为何这段简单的Swift嵌套for循环运行速度极慢?
性能瓶颈分析与优化方案
你的代码在iPhone上耗时10秒,核心原因主要有三个,逐个拆解:
1. 字符串随机访问的低效性
Swift的String不是随机访问集合——因为它基于Unicode编码,每个字符占用的字节数不固定。如果temp_1_characters是直接通过String下标访问(比如temp_1[k]),每次下标查找都会从字符串开头遍历到目标位置,时间复杂度是O(n)。80K次循环下来,这部分总时间复杂度会变成O(n²),直接拖慢整体速度。
2. 频繁字符串拼接的内存开销
temp_2是String类型,属于值类型。每次调用append或者+=操作,都会创建新的字符串实例并复制原有内容(内存不足时还会重新分配更大空间)。80K次拼接操作会触发大量内存分配和拷贝,这是另一个主要性能杀手。
3. 线性查找的额外开销
内层循环对cyph_2做线性查找,虽然每次最多65次遍历,但80K次外层循环累计下来是520万次操作,也会增加额外耗时。
优化后的代码示例
let cyph1: [Character] = my_array1 // 65个字符 let cyph2: [Character] = my_array2 // 65个字符 // 提前构建字符映射字典,把查找从O(n)改成O(1) var charMap: [Character: Character] = [:] for (index, char) in cyph2.enumerated() { charMap[char] = cyph1[index] } let temp1 = "80K long string, not that long" // 把字符串转成数组,实现O(1)随机访问 let temp1Chars = Array(temp1) // 预分配结果数组容量,避免频繁扩容 var resultChars: [Character] = [] resultChars.reserveCapacity(temp1Chars.count) for char in temp1Chars { // 直接通过字典查找映射字符 if let mappedChar = charMap[char] { resultChars.append(mappedChar) } else { resultChars.append(char) } } // 最后一次性转成字符串 let temp2 = String(resultChars)
优化点说明
- 字典映射:提前构建
cyph2到cyph1的字符映射,彻底消除嵌套循环的线性查找开销,把单次查找从O(65)降到O(1)。 - 数组化字符串:将原字符串转成
[Character]数组,保证每个字符的访问都是O(1)时间,避免字符串下标访问的低效问题。 - 预分配内存:给结果数组预分配足够容量,避免动态扩容带来的内存拷贝,最后一次性转成字符串,大幅减少内存操作次数。
经过这些优化,处理80K长度的字符串应该能控制在几毫秒内完成。
内容的提问来源于stack exchange,提问作者Numan Karaaslan
相关产品推荐
相关产品推荐

