最近去面试,面试官问了我这个问题。
有 k+1 堆大小1, 2^1, 2^2, 2^3, ...,2^k
。让我们stack 1, stack 2, ... stack k+1
分别称呼它们。当insert(x)
被调用时,元素被插入第一个堆栈,即大小为 1 的堆栈。如果该堆栈已满,则该堆栈的元素被移动到下一个堆栈,然后元素被插入第一个堆栈。它类似于管道操作。堆栈 1 将元素推入堆栈 2,堆栈 2 推入堆栈 3,依此类推。如果所有堆栈都已满,那么我们会抛出一个错误,说明堆栈溢出。还有另一个操作,delete(x)。它从堆栈堆栈中删除 x。因此,如果 x 不是最顶部的元素,即它不存在于堆栈 1 中,则我们从中弹出元素,然后移动元素,然后再次尝试弹出,直到找到该元素并将其删除。插入和删除此实现的摊销复杂度是多少?
编辑 1:展示插入和删除的工作原理。
假设有 2 个堆栈,堆栈 1 和堆栈 2 的大小分别为 2^0 和 2^1。
迭代 0:堆栈 1 -> {},堆栈 2 -> {}
迭代 1:插入(1)。堆栈 1 -> {1},堆栈 2 -> {},顶部 -> 1
迭代 2:插入(2)。堆栈 1 -> {2},堆栈 2 -> {1},顶部 -> 2
迭代 3:插入(3)。堆栈 1 -> {3},堆栈 2 -> {2,1},顶部 -> 3
迭代 4:插入(4)。溢出异常。堆栈 1 -> {3},堆栈 2 -> {2,1},顶部 -> 3
迭代 5:删除(2)。
- 我们弹出 3,作为 2!=3 并继续。堆栈 1 -> {2},堆栈 2 -> {1},顶部 -> 2
- 我们弹出 2 并返回。堆栈 1 -> {1},堆栈 2 -> {},顶部 -> 1
迭代 6:插入(4)。Stack 1 -> {4}, Stack 2 -> {1}, top -> 3
希望这两个操作现在都清楚了:)
我尽力而为,只能说出最坏情况的时间复杂度,即1+2^1+2^2+..+2^k
(几何级数总和)。我不是在寻找最坏情况的时间复杂度。我什至无法达到摊销的复杂性。任何人都可以帮助理解如何计算这个问题的摊销复杂度吗?