### Gather Merge
![[assets/ex_gathermerge.png|256]]
### The Explain Trace
```sql
-- Forcing a parallel sort and merge
SET max_parallel_workers_per_gather = 2;
SET min_parallel_table_scan_size = 0;
SET enable_indexscan = off;
EXPLAIN (ANALYZE, COSTS, BUFFERS, VERBOSE)
SELECT * FROM animals ORDER BY id;
```
```text
Gather Merge (cost=774.03..968.60 rows=16666 width=27) (actual time=4.327..5.298 rows=20000 loops=1)
Output: id, name, species_id, created_at
Workers Planned: 2
Workers Launched: 2
Buffers: shared hit=220
-> Sort (cost=774.00..794.84 rows=8333 width=27) (actual time=1.444..1.558 rows=6667 loops=3)
Output: id, name, species_id, created_at
Sort Key: animals.id
...
```
---
- **Description**: Collects and merges sorted results from parallel workers.
- **Performance**: High overhead due to Inter-Process Communication (IPC), but enables linear scaling for CPU-bound sorts.
- **Factors**: Number of workers, communication overhead, and the cost of the child sort nodes.
- **Cost**: `parallel worker cost + inter-process communication cost`
![[assets/ex_gather_merge.svg|256]]
- **Operates on**: [[Structures/Result Set]]
- **Workloads**:
- [[Workloads/IPC/Parallel/ExecuteGather|IPC: ExecuteGather]]
- [[Workloads/IPC/Parallel/ParallelFinish|IPC: ParallelFinish]]
- [[Workloads/LWLock/Parallel/ParallelQueryDSA|LWLock: ParallelQueryDSA]]
- [[Workloads/LWLock/Buffers/SharedTupleStore|LWLock: SharedTupleStore]]