0
我正在編寫一個模擬程序,其中一些操作員從一個隊列中取得工作。在每個時間步驟中,我需要依次檢查序列的元素,並且如果條件通過,則用隊列中的項目替換當前值。必須保留隊列中的剩餘部分以供後續迭代使用。使用隊列的修補程序序列
我寫過一個叫做patch
的程序來做到這一點,但它看起來並不是很整齊。有沒有一種更習慣的方式來實現同樣的目標?我希望它速度相當快,但仍然保持功能。
import scala.annotation.tailrec
import scala.collection.immutable.Queue
object SeqPimp extends App{
val mySeq = Seq('a', 'B', 'C', 'd', 'E')
val shortQ = Queue('+','-')
val longQ = Queue('+','-','*','/','%')
println(patch(mySeq)(_.isUpper, shortQ))
//Output: (List(a, +, -, d, E),Queue())
println(patch(mySeq)(_.isUpper, longQ))
//Output: (List(a, +, -, d, *),Queue(/, %))
def patch[T](to: Seq[T])(condition: T => Boolean, from: Queue[T]): (Seq[T], Queue[T]) = {
@tailrec
def go(acc: Seq[T], remaining: Seq[T], q: Queue[T]): (Seq[T], Queue[T]) = {
if(acc.size == to.size) (acc.reverse, q)
else if(q.size == 0) (acc.reverse ++: remaining, q)
else{
if(condition(remaining.head)){
val (item, q1) = q.dequeue
go(item +: acc, remaining.tail, q1)
}else{
go(remaining.head +: acc, remaining.tail, q)
}
}
}
go(Nil, to, from)
}
}
這似乎更清潔,只是一個恥辱,似乎慢了大約30%,我猜這是因爲索引訪問額外的遍歷。奇怪的是,將輸入切換到IndexedSeq將速度差距擴大到〜50%。 – Pengin
是的,性能很差。嘗試用'to.updated(i,from.head)'替換'to.patch(i,Seq(from.head),1)'..如果它更好。 。lemme知道..將編輯答案 – Shrey
編輯運行時間不到我原來的一半,而且行數也少!花了一些時間思考,看看爲什麼它更快。前瞻是很好的技巧。 – Pengin