Skip to content

Refactor par_sort_unstable to delegate to standard library#1283

Open
MatiasLopezING wants to merge 2 commits intorayon-rs:mainfrom
MatiasLopezING:update-unstable-sort
Open

Refactor par_sort_unstable to delegate to standard library#1283
MatiasLopezING wants to merge 2 commits intorayon-rs:mainfrom
MatiasLopezING:update-unstable-sort

Conversation

@MatiasLopezING
Copy link
Copy Markdown

As discussed in #1233, this PR delegates the sequential base cases of par_quicksort directly to the standard library (slice::sort_unstable_by), allowing Rayon to immediately benefit from the newly stabilized ipnsort algorithm.

Changes made:

  • Replaced internal fallbacks in recurse with v.sort_unstable_by().
  • Removed heapsort and its associated tests, as it is no longer needed as a degenerate-case fallback.
  • Kept par_mergesort untouched to avoid allocator contention issues for stable sorting (can be addressed in a future PR).

This removes the internal heapsort fallback and delegates the base cases of par_quicksort directly to slice::sort_unstable_by. This allows Rayon to take advantage of the newly stabilized ipnsort algorithm in the standard library for smaller sequential chunks, while drastically reducing internal code complexity. Addresses rayon-rs#1233 (Phase 1: Unstable sort)
Comment thread src/slice/sort.rs Outdated
// guarantee `O(n * log(n))` worst-case.
if limit == 0 {
heapsort(v, is_less);
v.sort_unstable_by(|a, b| if is_less(a, b) { cmp::Ordering::Less } else if is_less(b, a) { cmp::Ordering::Greater } else { cmp::Ordering::Equal });
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Adapting the predicate seems error prone and is done twice. Could this be factored out and done once earlier (without touching too much of the rest of the code)?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the review and guidance, @adamreichold! You were completely right.

Instead of doing the error-prone boolean conversion inside recurse, I refactored par_quicksort and its callers in src/slice/mod.rs to pass the Ordering comparator directly all the way down.

I also had to remove the random comparison test in src/slice/test.rs, since delegating to modern slice::sort_unstable_by strictly enforces total order and rightfully panics on completely random comparisons.

Just pushed the updates!

Refactored par_quicksort to take a comparison function returning Ordering directly, addressing feedback to avoid error-prone predicate conversions. Also removed an outdated test that deliberately violated total order, as modern Rust's sort_unstable_by strictly requires it and panics.
@cuviper
Copy link
Copy Markdown
Member

cuviper commented Apr 13, 2026

Closing and reopening to trigger CI again.

@cuviper cuviper closed this Apr 13, 2026
@cuviper cuviper reopened this Apr 13, 2026
Comment thread src/slice/sort.rs
let was_balanced = true;
// True if the last partitioning didn't shuffle elements (the slice was already partitioned).
let mut was_partitioned = true;
let was_partitioned = true;
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These flags have lost meaning if they're always true. Can we do anything to maintain them through recursion? Or should we just remove more dead code?

@cuviper
Copy link
Copy Markdown
Member

cuviper commented Apr 14, 2026

Overall, I'm not sure this is worth it just to remove one function, heapsort. Did you run any benchmarks to show that we gain by delegating to the standard library at this granularity?

@cuviper
Copy link
Copy Markdown
Member

cuviper commented Apr 14, 2026

In other words, a fuller port of the new std algorithms might be more fruitful, though more difficult.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants