新的Xcode (7.3)警告说,增量操作符++将在下一个swift3中删除。我使用了++的with循环(见下文)。在删除了增量操作符++之后,这个循环比使用++慢三倍。有什么更好的方法来改变这个时间循环呢?
在此之前
var first = string1.startIndex
var last = first.advancedBy(n, limit: string1.endIndex)
var myarray = [String]()
while last != string1.endIndex
{
myarray.append(string1[first++...last++])
}
之后
var first = string1.startIndex
var last = first.advancedBy(n, limit: string1.endIndex)
var myarray = [String]()
while last != string1.endIndex
{
myarray.append(string1[first...last])
first = first.advancedBy(1) // or first = first.successor()
last = first.advancedBy(n, limit: string1.endIndex) // or last = last.successor()
}
发布于 2016-03-23 14:38:29
使用预分配和随机访问分配,而不是重复将元素附加到数组中。
添加行first = ...
和last = ...
不应该像向未预先分配的数组重复添加元素(从而重复扩展数组)那样影响性能。如果初始化数组myarray
并使用随机访问(myarray[i]
)来分配滑动窗口字符串值,而不是使用.append(...)
,您应该能够减少开销。
var first = string1.startIndex
var last = first.advancedBy(n, limit: string1.endIndex)
var myarray = [String](count: string1.characters.count-n,
repeatedValue: "")
for i in 0..<myarray.count {
myarray[i] = string1[first...last]
first = first.advancedBy(1)
last = first.advancedBy(n, limit: string1.endIndex)
}
基准测试
我使用了下面的示例string1
和n
来对上面修改的解决方案与您自己的解决方案进行基准测试:
var string1 = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Fusce pretium diam at arcu suscipit, sed molestie mi rhoncus. Donec neque sapien, luctus ultricies ex sed, tristique auctor sem. Praesent varius ullamcorper nisi a commodo. Mauris eu rutrum enim, sit amet hendrerit velit. Curabitur iaculis neque ut tellus pretium, at convallis odio posuere. Integer ultricies diam ex, sit amet faucibus odio ultrices eu. Morbi tincidunt felis tellus, eget gravida est suscipit quis. Nam nunc ipsum, molestie sit amet neque at, aliquam maximus lacus. Sed bibendum massa a lorem eleifend, non eleifend felis commodo. Vivamus eget sem luctus, aliquam dolor nec, finibus diam. Morbi id justo vehicula, eleifend arcu nec, hendrerit neque. Donec ex ante, fringilla id rhoncus nec, porta id tortor. Donec dapibus nisl nibh, non posuere lacus egestas non. Duis massa quam, elementum sit amet volutpat eget, tincidunt sodales urna. Donec at congue ligula, a sollicitudin tortor."
string1 = string1+string1+string1 // 2880 characters
let n = 4
基准测试结果(使用-based function测量)
for i in ...
循环预初始化数组解决方案:2.5s.append(..)
解决方案与while
循环,如您的问题所示:32.5s如果执行时间很重要,显然您将受益于预先初始化数组和使用随机访问分配,而不是重复使用.append(..)
。
最后,您可以问自己是否真的需要显式地存储滑动窗口中的所有子字符串,或者是否足以存储与它们对应的范围。如果n
很大,上面的myarray
将包含大量的重复字符/重叠子串。在这种情况下,您最好只保存一个Range<String.CharacterView.Index>
元素数组,这些元素可以随时用于动态提取string1
的相关子字符串。例如:
var first = string1.startIndex
var last = first.advancedBy(n, limit: string1.endIndex)
var rangeArr = [Range<String.CharacterView.Index>](
count: string1.characters.count-n,
repeatedValue: first...last)
for i in 0..<rangeArr.count {
rangeArr[i] = first...last
first = first.advancedBy(1)
last = first.advancedBy(n, limit: string1.endIndex)
}
发布于 2016-03-23 13:40:22
将增量从first++
更改为first += 1
--这是关于不推荐版本的原则
但是,如果进行深入搜索,您可以发现increment
over String.CharacterView.Index
是实现自定义的后缀操作符,其中接受_Incrementable
协议的泛型,该协议声明了用于返回下一个链值的successor
方法。为什么++
比直接successor
更快?谁知道,显然有些优化正在开发中,而在中,Swift 3会有更好的速度。
发布于 2016-03-23 13:46:05
为什么不使用for循环而不是时间,然后直接使用索引进行访问。
var myarray = [String]()
for var i in string1.startIndex ... string1.endIndex {
myarray.append(string1[i])
}
希望这能有所帮助。
https://stackoverflow.com/questions/36189116
复制相似问题