Skip to content

Commit 93705b5

Browse files
committed
Optimize std::slice::range
Same reasoning as previous commit.
1 parent 80799aa commit 93705b5

File tree

1 file changed

+37
-20
lines changed

1 file changed

+37
-20
lines changed

library/core/src/slice/index.rs

Lines changed: 37 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -911,6 +911,7 @@ where
911911

912912
ops::Bound::Excluded(&end) if end > len => slice_index_fail(0, end, len),
913913
ops::Bound::Excluded(&end) => end,
914+
914915
ops::Bound::Unbounded => len,
915916
};
916917

@@ -966,19 +967,29 @@ where
966967
{
967968
let len = bounds.end;
968969

969-
let start = match range.start_bound() {
970-
ops::Bound::Included(&start) => start,
971-
ops::Bound::Excluded(start) => start.checked_add(1)?,
972-
ops::Bound::Unbounded => 0,
973-
};
974-
975970
let end = match range.end_bound() {
976-
ops::Bound::Included(end) => end.checked_add(1)?,
971+
ops::Bound::Included(&end) if end >= len => return None,
972+
// Cannot overflow because `end < len` implies `end < usize::MAX`.
973+
ops::Bound::Included(end) => end + 1,
974+
975+
ops::Bound::Excluded(&end) if end > len => return None,
977976
ops::Bound::Excluded(&end) => end,
977+
978978
ops::Bound::Unbounded => len,
979979
};
980980

981-
if start > end || end > len { None } else { Some(ops::Range { start, end }) }
981+
let start = match range.start_bound() {
982+
ops::Bound::Excluded(&start) if start >= end => return None,
983+
// Cannot overflow because `start < end` implies `start < usize::MAX`.
984+
ops::Bound::Excluded(&start) => start + 1,
985+
986+
ops::Bound::Included(&start) if start > end => return None,
987+
ops::Bound::Included(&start) => start,
988+
989+
ops::Bound::Unbounded => 0,
990+
};
991+
992+
Some(ops::Range { start, end })
982993
}
983994

984995
/// Converts a pair of `ops::Bound`s into `ops::Range` without performing any
@@ -1007,21 +1018,27 @@ pub(crate) fn into_range(
10071018
len: usize,
10081019
(start, end): (ops::Bound<usize>, ops::Bound<usize>),
10091020
) -> Option<ops::Range<usize>> {
1010-
use ops::Bound;
1011-
let start = match start {
1012-
Bound::Included(start) => start,
1013-
Bound::Excluded(start) => start.checked_add(1)?,
1014-
Bound::Unbounded => 0,
1015-
};
1016-
10171021
let end = match end {
1018-
Bound::Included(end) => end.checked_add(1)?,
1019-
Bound::Excluded(end) => end,
1020-
Bound::Unbounded => len,
1022+
ops::Bound::Included(end) if end >= len => return None,
1023+
// Cannot overflow because `end < len` implies `end < usize::MAX`.
1024+
ops::Bound::Included(end) => end + 1,
1025+
1026+
ops::Bound::Excluded(end) if end > len => return None,
1027+
ops::Bound::Excluded(end) => end,
1028+
1029+
ops::Bound::Unbounded => len,
10211030
};
10221031

1023-
// Don't bother with checking `start < end` and `end <= len`
1024-
// since these checks are handled by `Range` impls
1032+
let start = match start {
1033+
ops::Bound::Excluded(start) if start >= end => return None,
1034+
// Cannot overflow because `start < end` implies `start < usize::MAX`.
1035+
ops::Bound::Excluded(start) => start + 1,
1036+
1037+
ops::Bound::Included(start) if start > end => return None,
1038+
ops::Bound::Included(start) => start,
1039+
1040+
ops::Bound::Unbounded => 0,
1041+
};
10251042

10261043
Some(start..end)
10271044
}

0 commit comments

Comments
 (0)