Concurrency
1. Synchronous Operations¶
Synchronous execution is the default mode where operations are performed one after another.
- Mechanism: A process typically starts with one main thread. When a request is made (e.g., reading from a disk or a network call), the thread waits for the operation to complete [00:27].
- Blocking: Even if the thread isn't doing active work (like waiting for a disk controller), it remains blocked. The rest of the code cannot execute until that specific task finishes [01:24].
- Impact on UX: In single-threaded applications, synchronous operations can cause the User Interface (UI) to freeze because the thread is too busy waiting to handle user interactions like button clicks [02:40].
2. Multithreading¶
To solve blocking issues, developers often spin up additional threads within a single process.
- Definition: A thread is an execution unit within a process "container" [03:47].
- Resource Sharing: All threads within a process share the same memory and resources. This is a double-edged sword: it allows for fast communication but leads to race conditions [04:07].
- Complexity: Managing multiple threads requires "thread safety" using mutexes and locks to prevent threads from accessing the same data simultaneously [04:51].
- Parallelism: On multi-core CPUs, threads can execute literally in parallel, not just via time-slicing [05:45].
3. Asynchronous Operations¶
Asynchronous programming allows a single thread to handle multiple tasks without blocking.
- Definition: A single-threaded, non-blocking framework (like Node.js) [06:02].
- The "Call Me Back" Pattern: Instead of waiting for an IO task to finish, the thread sends the request and provides a callback function. The thread then moves on to execute other code immediately [08:08].
- Event Loop: The thread continuously checks an "event loop" to see if any background tasks (like a disk read) have finished and triggered their callbacks [08:39].
- Evolution of Code:
- Callbacks: Historically led to "callback hell" (deeply nested, unreadable code) [09:16].
- Promises: Introduced to make async code more manageable [10:07].
- Async/Await: The modern standard that provides "syntactical sugar," allowing asynchronous code to look like readable synchronous code [10:22].
4. Multiprocessing¶
Multiprocessing involves running multiple independent processes rather than multiple threads in one process.
- Isolation: Each process has its own dedicated memory and resources, making it more stable and isolated than threads [11:45].
- Communication: Since they don't share memory, processes communicate via Inter-Process Communication (IPC), such as Redis, sockets, or local ports [12:03].
- Scalability: Multiprocessing is excellent for CPU-intensive tasks (e.g., brute-forcing hashes) because tasks can be split and distributed across different CPU cores or even different machines [12:59].
- Example: Containers (like Docker) are essentially isolated processes [13:08].
Comparison Summary¶
| Feature | Synchronous | Asynchronous | Multithreading | Multiprocessing |
|---|---|---|---|---|
| Threads | Single | Single | Multiple | Multiple Processes |
| Blocking | Yes | No | No (usually) | No (isolated) |
| Best For | Simple scripts | IO-bound tasks (Web) | Parallel tasks | CPU-bound tasks |
| Complexity | Low | Medium | High (locks/races) | Medium (IPC) |