Stack (ADT)

Context: FIT1008_MOC Β· a LIFO Abstract Data Type (ADT) Β· backbone clustering its ArrayStack and LinkStack implementations Β· contract via Abstract Base Class

Quick Revision

  • 🎯 Objective: LIFO top-only access βž” the ADT behind the call stack, recursion/DFS, expression evaluation.
  • πŸ“¦ Core Components: Contract βž” ABC push/pop/peek | ArrayStack βž” contiguous, fixed/growable | LinkStack βž” Node chain, never full.
  • ⚑ Key Constraint: all ops βž” decision is space: wasted array slack vs one pointer/node (crossover β‰ˆ half-full).

πŸ“ Core

1. Stack Contract (LIFO)

  • LIFO discipline βž” push/pop/peek act only at the top; last-in-first-out.
  • Interface βž” push Β· pop Β· peek Β· is_empty Β· is_full Β· __len__ Β· clear.
  • ABC split βž” storage-independent (__len__, is_empty) concrete | push/pop/peek/is_full @abstractmethod | Stack() βž” TypeError.

2. ArrayStack (Array-Backed)

  • Storage substrate βž” fixed Array (Data Structure) + int length; top = length-1.
  • Structural invariant βž” valid data in 0..length-1 (Invariant); beyond = garbage.
  • Growth mode βž” fixed raises on overflow | growable doubles βž” push amortised (Dynamic Array Resizing).

3. LinkStack (Linked)

  • Storage substrate βž” Node chain + single top pointer at head.
  • Pointer mechanics βž” push βž” new.link=top | top=new; pop βž” top=top.link (old node GC’d).
  • Never full βž” no is_full, no resize; memory shrinks on pop β€” a fixed array cannot.

βš™οΈ Core Implementation

πŸ”Ή Abstract Base β€” the contract

πŸ”Ή ArrayStack

πŸ”Ή LinkStack

βš–οΈ Core Decision Matrix

Variant / StrategyTrigger ConditionAdvantage (Pro)Disadvantage (Con) / Complexity BoundCache / Memory Impact
ArrayStack (fixed)Capacity known, dense push/pop/peekraises if full; wastes slackcontiguous, cache-friendly
ArrayStack (growable)Unknown but bounded amortised pushresize copy worstcontiguous, doubles on grow
LinkStackVariable / unboundedtrue , never full pointer/node; no random accessscattered, poor locality

When It Flips: array of capacity holding uses ; LinkStack uses βž” LinkStack wins when (array under half-full), ArrayStack wins when nearly full.

πŸ“Š Exam Execution Trace

Manual Execution Trace

ArrayStack(3): push 7, push 4, pop, push 9, peek

Step / StateTrigger Oparray (cap 3)lengthTop idxReturn Payload
0 (Init)init[_, _, _]0
1push 7[7, _, _]10
2push 4[7, 4, _]21
3pop[7, 4, _]104
4push 9[7, 9, _]21
5peek[7, 9, _]219

Applied Exercise

Problem: Bound the cost of pushes on a doubling ArrayStack. Derivation Proof / Hand-Calculation Walkthrough:

Final Extracted Output: push is amortised (not worst-case); a single resize is .

🧠 Active Recall