Code Explanation:
1. Import ExitStack
from contextlib import ExitStack
ExitStack is a class from Python's contextlib module.
It allows us to register multiple cleanup actions dynamically and execute them automatically when the with block exits.
2. Create an Empty List
events = []
An empty list named events is created.
Initially:
events = []
This list will store "A", "B", and "C".
3. Start the ExitStack
with ExitStack() as stack:
This creates an active ExitStack context.
The code inside the with block executes normally.
When Python leaves the with block, ExitStack automatically executes all registered callbacks.
Conceptually:
Enter ExitStack
↓
Execute with-block
↓
Exit with-block
↓
Execute registered callbacks
4. Register Callback "A"
stack.callback(events.append, "A")
This does not immediately execute:
events.append("A")
Instead, it registers that function call as a callback to be executed when the ExitStack exits.
So at this point:
events = []
The callback is waiting in the stack.
5. Register Callback "B"
stack.callback(events.append, "B")
Again, "B" is not immediately added to the list.
Another callback is registered.
Conceptually, the stack now contains:
A
B
But callbacks are executed using LIFO (Last In, First Out) order.
Therefore, "B" will execute before "A".
6. Append "C" Normally
events.append("C")
This is a normal list operation.
Unlike stack.callback(), it executes immediately.
So now:
events = ['C']
7. Exit the with Block
After:
events.append("C")
the with block ends.
Now ExitStack starts executing its registered callbacks.
The callbacks were registered in this order:
A → B
But they execute in reverse order:
B → A
This is the LIFO principle.
8. Execute Callback "B"
The first callback executed is effectively:
events.append("B")
Now:
events = ['C', 'B']
9. Execute Callback "A"
The next callback is:
events.append("A")
Now:
events = ['C', 'B', 'A']
10. Print the Result
print(events)
The final list is:
['C', 'B', 'A']
Therefore, the output is:
['C', 'B', 'A']

0 Comments:
Post a Comment