Skip to content

perf: use ShardMergeReader for non-PQ index types#6289

Closed
hushengquan wants to merge 1 commit intolance-format:mainfrom
hushengquan:optimize-distributed-index
Closed

perf: use ShardMergeReader for non-PQ index types#6289
hushengquan wants to merge 1 commit intolance-format:mainfrom
hushengquan:optimize-distributed-index

Conversation

@hushengquan
Copy link
Copy Markdown
Contributor

@hushengquan hushengquan commented Mar 25, 2026

Problem Description

When processing the merge_partial_vector_auxiliary_files stage for the ivf-sq index on a dataset of 5 million records with 8 workers and 2236 partitions, the operation takes an excessively long time (3780 seconds), which significantly impacts the overall efficiency of vector index merging.(#6288 )

Root Cause

The current implementation of merging partial vector auxiliary files lacks shard-based parallelism optimization, leading to serial processing bottlenecks when handling a large number of partitions and datasets.

Proposed Solution

Use ShardMergeReader to leverage shard-level parallelism for merging partial vector auxiliary files. This optimization distributes the merge workload across multiple shards, reducing the overall processing time.

Performance Metrics (Before/After)

Scenario (8 workers / 2236 partitions / 5M dataset) Before Optimization After Optimization Improvement
merge_partial_vector_auxiliary_files (ivf_sq index) 3780 seconds 208 seconds ~18.1x faster

Additional Context

  • Index type: ivf_sq
  • Dataset size: 5 million records
  • Worker count: 8
  • Partition count: 2236
  • Optimization core: ShardMergeReader (shard-based parallel merge logic)

@github-actions
Copy link
Copy Markdown
Contributor

PR Review

Clean change — reusing ShardMergeReader for non-PQ paths is the obvious fix and the 8.8x improvement speaks for itself.

Two items to address:

1. Dead code: write_partition_rows (P1)

After this PR, pub async fn write_partition_rows(...) (line ~290) has zero callers — the only call site was the code you replaced. It should be removed in this PR to avoid a dead-code warning (it's pub but not used outside this file/crate).

2. Missing empty-batches guard (P1 — consistency)

The PQ path (lines 1231-1236) returns an error when batches.is_empty() for a partition with accumulated_lengths[pid] > 0. The new non-PQ path silently skips this case. Consider adding the same guard for consistency, or document why it's intentionally omitted.


Otherwise LGTM. Existing test_merge_ivf_flat_success_basic covers this path. Nice improvement.

@hushengquan hushengquan force-pushed the optimize-distributed-index branch from 705e076 to 719c2e6 Compare March 25, 2026 06:28
@codecov
Copy link
Copy Markdown

codecov bot commented Mar 25, 2026

Codecov Report

❌ Patch coverage is 70.83333% with 7 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
...lance-index/src/vector/distributed/index_merger.rs 70.83% 4 Missing and 3 partials ⚠️

📢 Thoughts on this report? Let us know!

@Xuanwo
Copy link
Copy Markdown
Collaborator

Xuanwo commented Apr 1, 2026

Thank you very much for this PR! I think this change is great, but I want to raise one point: we are also limited by memory usage. A non-PQ index uses more memory than a PQ index, that’s why we didn’t have this feature in the first place.

IVF_SQ/IVF_FLAT can have large payloads and large partitions. Therefore, I believe we should ensure our new logic works well in multi‑batch and large‑partition scenarios, and make sure we do not store an entire partition in memory before writing it out.

@hushengquan
Copy link
Copy Markdown
Contributor Author

Thank you very much for this PR! I think this change is great, but I want to raise one point: we are also limited by memory usage. A non-PQ index uses more memory than a PQ index, that’s why we didn’t have this feature in the first place.

IVF_SQ/IVF_FLAT can have large payloads and large partitions. Therefore, I believe we should ensure our new logic works well in multi‑batch and large‑partition scenarios, and make sure we do not store an entire partition in memory before writing it out.

Got it, thank you!

@hushengquan hushengquan closed this Apr 1, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants