Skip to content

Conversation

@tisonkun
Copy link
Contributor

@tisonkun tisonkun commented Nov 25, 2025

This refers to #149046.

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-libs Relevant to the library team, which will review and decide on the PR/issue. labels Nov 25, 2025
@rustbot
Copy link
Collaborator

rustbot commented Nov 25, 2025

r? @scottmcm

rustbot has assigned @scottmcm.
They will have a look at your PR within the next two weeks and either review your PR or reassign to another reviewer.

Use r? to explicitly pick a reviewer

@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

Signed-off-by: tison <wander4096@gmail.com>
@tisonkun tisonkun force-pushed the slice_partial_sort_unstable branch from 115ac5c to 0e87d5d Compare November 25, 2025 16:42
Signed-off-by: tison <wander4096@gmail.com>
@tisonkun
Copy link
Contributor Author

cc @orlp

Copy link
Contributor

@orlp orlp left a comment

Choose a reason for hiding this comment

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

Left some remarks, some on style, but also some with substance.

Besides comments on the code that's written, I do note a lack of tests?

View changes since this review

/// as if the whole slice were sorted in ascending order.
///
/// This sort is unstable (i.e., may reorder equal elements), in-place (i.e., does not
/// allocate), and *O*(*n* + *k* \* log(*k*)) worst-case.
Copy link
Contributor

Choose a reason for hiding this comment

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

It's not specified what k is.

///
/// If the implementation of [`Ord`] for `T` does not implement a [total order], the function
/// may panic; even if the function exits normally, the resulting order of elements in the slice
/// is unspecified. See also the note on panicking below.
Copy link
Contributor

Choose a reason for hiding this comment

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

I don't think we need to repeat the entire comment with examples from sort_unstable_by here, I think we can just refer the reader to its comment. This concerns this paragraph as well as all following paragraphs up until # Panics.

where
F: FnMut(&T, &T) -> Ordering,
R: RangeBounds<usize>,
{
Copy link
Contributor

Choose a reason for hiding this comment

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

I think this implementation should be under sort::unstable::partial_sort instead, and like its cousin sort::unstable::sort take a function returning a boolean. Then partial_sort_unstable(_by(_key)) can all dispatch to that one directly.

/// Partially sorts the slice in ascending order **without** preserving the initial order of equal elements.
///
/// Upon completion, the elements in the specified `range` will be the elements of the slice
/// as if the whole slice were sorted in ascending order.
Copy link
Contributor

Choose a reason for hiding this comment

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

This is missing the guarantees I mentioned in my comment on the ACP about the elements that come before and after the sorted range.

let Range { start, end } = slice::range(range, ..len);

if start + 1 > end {
// target range is empty, nothing to do
Copy link
Contributor

Choose a reason for hiding this comment

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

This is incorrect if we do provide the guarantees for elements before and after the range I mentioned in my comment on the ACP. I think those guarantees are more useful than allowing the partial sort by an empty range in the middle to be a no-op.

let len = self.len();
let Range { start, end } = slice::range(range, ..len);

if start + 1 > end {
Copy link
Contributor

Choose a reason for hiding this comment

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

What a very strange way to write start == end. slice::range already disallows inverted ranges.

return;
}

let index = start;
Copy link
Contributor

Choose a reason for hiding this comment

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

I think assigning start to a variable which is used only once and is later shadowed with a different definition is not a good idea. Just directly pass start to partition_at_index IMO.

let (_, _, rest) =
sort::select::partition_at_index(self, index, |a, b| compare(a, b) == Less);

if start + 2 > end {
Copy link
Contributor

Choose a reason for hiding this comment

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

Again, very strange way to write end - start == 1. I think this branch is worthwhile though, select_nth_unstable does guarantee that this singular element is in its correct place.

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

Labels

S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-libs Relevant to the library team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants