-
Notifications
You must be signed in to change notification settings - Fork 12.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Check for exhaustion in RangeInclusive::contains and slicing #78109
Conversation
When a range has finished iteration, `is_empty` returns true, so it should also be the case that `contains` returns false.
r? @shepmaster (rust_highfive has picked a reviewer for you, use r? to override) |
This might want @rust-lang/libs FCP per #77941 (comment). |
I've moved the |
I don't know why the end should be treated specially. If you think this is useful, shouldn't it apply to all parts of iteration equally, and |
This is about The inclusive end is special by nature, that's the whole point. Once the iterator reaches |
Got it, thanks, I didn't realize this was fixing an omission. Looks good to me then :) Also, wow, |
It would also be nice to have some tests that check this behaviour |
@rust-lang/libs: this PR changes the implementation of RangeBounds for RangeInclusive in such a way that the following assertions succeed. Previously fn main() {
let mut range = 0..=0;
assert!(!range.is_empty());
assert!(range.contains(&0));
range.next();
assert!(range.is_empty());
assert!(!range.contains(&0));
} Another example of the behavior change: fn main() {
let array = ['w', 'x', 'y', 'z'];
let mut range = 0..=3;
while let Some(i) = range.next() {
println!(
"after i={}, the remaining elements are {:?}",
i, &array[range.clone()],
);
}
} Old behavior: after i=0, the remaining elements are ['x', 'y', 'z'] after i=1, the remaining elements are ['y', 'z'] after i=2, the remaining elements are ['z'] after i=3, the remaining elements are ['z'] New behavior: after i=0, the remaining elements are ['x', 'y', 'z'] after i=1, the remaining elements are ['y', 'z'] after i=2, the remaining elements are ['z'] after i=3, the remaining elements are [] @rfcbot fcp merge |
Team member @dtolnay has proposed to merge this. The next step is review by the rest of the tagged team members: No concerns currently listed. Once a majority of reviewers approve (and at most 2 approvals are outstanding), this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up! See this document for info about what commands tagged team members can give me. |
@SkiFire13 I figured the doc-test was sufficient -- I don't see any other existing tests of ranged @dtolnay this doesn't actually affect slicing (yet) because |
Let's consider both as part of this FCP. I imagine we'd not want to do one without the other. But the code change for SliceIndex can go in either this PR or separate PR if easier. |
Preserving bounds checking for exhausted |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Implementation looks good to me. Thank you @cuviper.
🔔 This is now entering its final comment period, as per the review above. 🔔 |
@bors r+ |
📌 Commit 9202fbd has been approved by |
🌲 The tree is currently closed for pull requests below priority 1000, this pull request will be tested once the tree is reopened |
…as-schievink Rollup of 15 pull requests Successful merges: - rust-lang#76649 (Add a spin loop hint for Arc::downgrade) - rust-lang#77392 (add `insert` to `Option`) - rust-lang#77716 (Revert "Allow dynamic linking for iOS/tvOS targets.") - rust-lang#78109 (Check for exhaustion in RangeInclusive::contains and slicing) - rust-lang#78198 (Simplify assert terminator only if condition evaluates to expected value) - rust-lang#78243 (--test-args flag description) - rust-lang#78249 (improve const infer error) - rust-lang#78250 (Document inline-const) - rust-lang#78264 (Add regression test for issue-77475) - rust-lang#78274 (Update description of Empty Enum for accuracy) - rust-lang#78278 (move `visit_predicate` into `TypeVisitor`) - rust-lang#78292 (Loop instead of recursion) - rust-lang#78293 (Always store Rustdoc theme when it's changed) - rust-lang#78300 (Make codegen coverage_context optional, and check) - rust-lang#78307 (Revert "Set .llvmbc and .llvmcmd sections as allocatable") Failed merges: r? `@ghost`
Pkgsrc changes: * Adjust patches, convert tabs to spaces so that tests pass. * Remove patches which are no longer needed (upstream changed) * Minor adjustments for SunOS, e.g. disable stack probes. * Adjust cargo checksum patching accordingly. * Remove commented-out use of PATCHELF on NetBSD, which doesn't work anyway... Upstream changes: Version 1.49.0 (2020-12-31) ============================ Language ----------------------- - [Unions can now implement `Drop`, and you can now have a field in a union with `ManuallyDrop<T>`.][77547] - [You can now cast uninhabited enums to integers.][76199] - [You can now bind by reference and by move in patterns.][76119] This allows you to selectively borrow individual components of a type. E.g. ```rust #[derive(Debug)] struct Person { name: String, age: u8, } let person = Person { name: String::from("Alice"), age: 20, }; // `name` is moved out of person, but `age` is referenced. let Person { name, ref age } = person; println!("{} {}", name, age); ``` Compiler ----------------------- - [Added tier 1\* support for `aarch64-unknown-linux-gnu`.][78228] - [Added tier 2 support for `aarch64-apple-darwin`.][75991] - [Added tier 2 support for `aarch64-pc-windows-msvc`.][75914] - [Added tier 3 support for `mipsel-unknown-none`.][78676] - [Raised the minimum supported LLVM version to LLVM 9.][78848] - [Output from threads spawned in tests is now captured.][78227] - [Change os and vendor values to "none" and "unknown" for some targets][78951] \* Refer to Rust's [platform support page][forge-platform-support] for more information on Rust's tiered platform support. Libraries ----------------------- - [`RangeInclusive` now checks for exhaustion when calling `contains` and indexing.][78109] - [`ToString::to_string` now no longer shrinks the internal buffer in the default implementation.][77997] - [`ops::{Index, IndexMut}` are now implemented for fixed sized arrays of any length.][74989] Stabilized APIs --------------- - [`slice::select_nth_unstable`] - [`slice::select_nth_unstable_by`] - [`slice::select_nth_unstable_by_key`] The following previously stable methods are now `const`. - [`Poll::is_ready`] - [`Poll::is_pending`] Cargo ----------------------- - [Building a crate with `cargo-package` should now be independently reproducible.][cargo/8864] - [`cargo-tree` now marks proc-macro crates.][cargo/8765] - [Added `CARGO_PRIMARY_PACKAGE` build-time environment variable.] [cargo/8758] This variable will be set if the crate being built is one the user selected to build, either with `-p` or through defaults. - [You can now use glob patterns when specifying packages & targets.][cargo/8752] Compatibility Notes ------------------- - [Demoted `i686-unknown-freebsd` from host tier 2 to target tier 2 support.][78746] - [Macros that end with a semi-colon are now treated as statements even if they expand to nothing.][78376] - [Rustc will now check for the validity of some built-in attributes on enum variants.][77015] Previously such invalid or unused attributes could be ignored. - Leading whitespace is stripped more uniformly in documentation comments, which may change behavior. You read [this post about the changes][rustdoc-ws-post] for more details. - [Trait bounds are no longer inferred for associated types.][79904] Internal Only ------------- These changes provide no direct user facing benefits, but represent significant improvements to the internals and overall performance of rustc and related tools. - [rustc's internal crates are now compiled using the `initial-exec` Thread Local Storage model.][78201] - [Calculate visibilities once in resolve.][78077] - [Added `system` to the `llvm-libunwind` bootstrap config option.][77703] - [Added `--color` for configuring terminal color support to bootstrap.][79004] [75991]: rust-lang/rust#75991 [78951]: rust-lang/rust#78951 [78848]: rust-lang/rust#78848 [78746]: rust-lang/rust#78746 [78376]: rust-lang/rust#78376 [78228]: rust-lang/rust#78228 [78227]: rust-lang/rust#78227 [78201]: rust-lang/rust#78201 [78109]: rust-lang/rust#78109 [78077]: rust-lang/rust#78077 [77997]: rust-lang/rust#77997 [77703]: rust-lang/rust#77703 [77547]: rust-lang/rust#77547 [77015]: rust-lang/rust#77015 [76199]: rust-lang/rust#76199 [76119]: rust-lang/rust#76119 [75914]: rust-lang/rust#75914 [74989]: rust-lang/rust#74989 [79004]: rust-lang/rust#79004 [78676]: rust-lang/rust#78676 [79904]: rust-lang/rust#79904 [cargo/8864]: rust-lang/cargo#8864 [cargo/8765]: rust-lang/cargo#8765 [cargo/8758]: rust-lang/cargo#8758 [cargo/8752]: rust-lang/cargo#8752 [`slice::select_nth_unstable`]: https://doc.rust-lang.org/nightly/std/primitive.slice.html#method.select_nth_unstable [`slice::select_nth_unstable_by`]: https://doc.rust-lang.org/nightly/std/primitive.slice.html#method.select_nth_unstable_by [`slice::select_nth_unstable_by_key`]: https://doc.rust-lang.org/nightly/std/primitive.slice.html#method.select_nth_unstable_by_key [`hint::spin_loop`]: https://doc.rust-lang.org/stable/std/hint/fn.spin_loop.html [`Poll::is_ready`]: https://doc.rust-lang.org/stable/std/task/enum.Poll.html#method.is_ready [`Poll::is_pending`]: https://doc.rust-lang.org/stable/std/task/enum.Poll.html#method.is_pending [rustdoc-ws-post]: https://blog.guillaume-gomez.fr/articles/2020-11-11+New+doc+comment+handling+in+rustdoc
When a range has finished iteration,
is_empty
returns true, so itshould also be the case that
contains
returns false.Fixes #77941.