1
Fork 0

Rollup merge of #81154 - dylni:improve-design-of-assert-len, r=KodrAus

Improve design of `assert_len`

It was discussed in the [tracking issue](https://github.com/rust-lang/rust/issues/76393#issuecomment-761765448) that `assert_len`'s name and usage are confusing. This PR improves them based on a suggestion by ``@scottmcm`` in that issue.

I also improved the documentation to make it clearer when you might want to use this method.

Old example:

```rust
let range = range.assert_len(slice.len());
```

New example:

```rust
let range = range.ensure_subset_of(..slice.len());
```

Fixes #81157
This commit is contained in:
Dylan DPC 2021-02-23 02:51:43 +01:00 committed by GitHub
commit 72e6d51583
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
9 changed files with 117 additions and 113 deletions

View file

@ -1063,7 +1063,7 @@ impl<T> VecDeque<T> {
where
R: RangeBounds<usize>,
{
let Range { start, end } = range.assert_len(self.len());
let Range { start, end } = slice::range(range, ..self.len());
let tail = self.wrap_add(self.tail, start);
let head = self.wrap_add(self.tail, end);
(tail, head)

View file

@ -115,7 +115,6 @@
#![feature(or_patterns)]
#![feature(pattern)]
#![feature(ptr_internals)]
#![feature(range_bounds_assert_len)]
#![feature(rustc_attrs)]
#![feature(receiver_trait)]
#![cfg_attr(bootstrap, feature(min_const_generics))]
@ -123,6 +122,7 @@
#![feature(set_ptr_value)]
#![feature(slice_ptr_get)]
#![feature(slice_ptr_len)]
#![feature(slice_range)]
#![feature(staged_api)]
#![feature(str_internals)]
#![feature(trusted_len)]

View file

@ -92,6 +92,8 @@ use crate::borrow::ToOwned;
use crate::boxed::Box;
use crate::vec::Vec;
#[unstable(feature = "slice_range", issue = "76393")]
pub use core::slice::range;
#[unstable(feature = "array_chunks", issue = "74985")]
pub use core::slice::ArrayChunks;
#[unstable(feature = "array_chunks", issue = "74985")]

View file

@ -49,6 +49,7 @@ use core::iter::{FromIterator, FusedIterator};
use core::ops::Bound::{Excluded, Included, Unbounded};
use core::ops::{self, Add, AddAssign, Index, IndexMut, Range, RangeBounds};
use core::ptr;
use core::slice;
use core::str::{lossy, pattern::Pattern};
use crate::borrow::{Cow, ToOwned};
@ -1510,14 +1511,14 @@ impl String {
// of the vector version. The data is just plain bytes.
// Because the range removal happens in Drop, if the Drain iterator is leaked,
// the removal will not happen.
let Range { start, end } = range.assert_len(self.len());
let Range { start, end } = slice::range(range, ..self.len());
assert!(self.is_char_boundary(start));
assert!(self.is_char_boundary(end));
// Take out two simultaneous borrows. The &mut String won't be accessed
// until iteration is over, in Drop.
let self_ptr = self as *mut _;
// SAFETY: `assert_len` and `is_char_boundary` do the appropriate bounds checks.
// SAFETY: `slice::range` and `is_char_boundary` do the appropriate bounds checks.
let chars_iter = unsafe { self.get_unchecked(start..end) }.chars();
Drain { start, end, iter: chars_iter, string: self_ptr }

View file

@ -1651,7 +1651,7 @@ impl<T, A: Allocator> Vec<T, A> {
// the hole, and the vector length is restored to the new length.
//
let len = self.len();
let Range { start, end } = range.assert_len(len);
let Range { start, end } = slice::range(range, ..len);
unsafe {
// set self.vec length's to start, to be safe in case Drain is leaked
@ -2037,11 +2037,11 @@ impl<T: Clone, A: Allocator> Vec<T, A> {
where
R: RangeBounds<usize>,
{
let range = src.assert_len(self.len());
let range = slice::range(src, ..self.len());
self.reserve(range.len());
// SAFETY:
// - `assert_len` guarantees that the given range is valid for indexing self
// - `slice::range` guarantees that the given range is valid for indexing self
unsafe {
self.spec_extend_from_within(range);
}