about summary refs log tree commit diff
path: root/src/libcore/tests
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2018-06-17 07:49:25 +0000
committerbors <bors@rust-lang.org>2018-06-17 07:49:25 +0000
commitaec00f97e1cdcea2b079e209a7e759201ba6ca7c (patch)
tree4ed19581adc5d794890fbf515848d2432b96a559 /src/libcore/tests
parent0f8f4903f73a21d7f408870551c08acd051abeb0 (diff)
parent2a999b4b525ed8b4f735e233cc065b292d3eeb03 (diff)
downloadrust-aec00f97e1cdcea2b079e209a7e759201ba6ca7c.tar.gz
rust-aec00f97e1cdcea2b079e209a7e759201ba6ca7c.zip
Auto merge of #51466 - joshlf:ref-split, r=dtolnay
Add Ref/RefMut map_split method

As proposed [here](https://internals.rust-lang.org/t/make-refcell-support-slice-splitting/7707).

TLDR: Add a `map_split` method that allows multiple `RefMut`s to exist simultaneously so long as they refer to non-overlapping regions of the original `RefCell`. This is useful for things like the slice `split_at_mut` method.
Diffstat (limited to 'src/libcore/tests')
-rw-r--r--src/libcore/tests/cell.rs58
-rw-r--r--src/libcore/tests/lib.rs1
2 files changed, 59 insertions, 0 deletions
diff --git a/src/libcore/tests/cell.rs b/src/libcore/tests/cell.rs
index 962fb2f0e02..4b7243b9cfc 100644
--- a/src/libcore/tests/cell.rs
+++ b/src/libcore/tests/cell.rs
@@ -166,6 +166,64 @@ fn ref_map_does_not_update_flag() {
 }
 
 #[test]
+fn ref_map_split_updates_flag() {
+    let x = RefCell::new([1, 2]);
+    {
+        let b1 = x.borrow();
+        assert!(x.try_borrow().is_ok());
+        assert!(x.try_borrow_mut().is_err());
+        {
+            let (_b2, _b3) = Ref::map_split(b1, |slc| slc.split_at(1));
+            assert!(x.try_borrow().is_ok());
+            assert!(x.try_borrow_mut().is_err());
+        }
+        assert!(x.try_borrow().is_ok());
+        assert!(x.try_borrow_mut().is_ok());
+    }
+    assert!(x.try_borrow().is_ok());
+    assert!(x.try_borrow_mut().is_ok());
+
+    {
+        let b1 = x.borrow_mut();
+        assert!(x.try_borrow().is_err());
+        assert!(x.try_borrow_mut().is_err());
+        {
+            let (_b2, _b3) = RefMut::map_split(b1, |slc| slc.split_at_mut(1));
+            assert!(x.try_borrow().is_err());
+            assert!(x.try_borrow_mut().is_err());
+            drop(_b2);
+            assert!(x.try_borrow().is_err());
+            assert!(x.try_borrow_mut().is_err());
+        }
+        assert!(x.try_borrow().is_ok());
+        assert!(x.try_borrow_mut().is_ok());
+    }
+    assert!(x.try_borrow().is_ok());
+    assert!(x.try_borrow_mut().is_ok());
+}
+
+#[test]
+fn ref_map_split() {
+    let x = RefCell::new([1, 2]);
+    let (b1, b2) = Ref::map_split(x.borrow(), |slc| slc.split_at(1));
+    assert_eq!(*b1, [1]);
+    assert_eq!(*b2, [2]);
+}
+
+#[test]
+fn ref_mut_map_split() {
+    let x = RefCell::new([1, 2]);
+    {
+        let (mut b1, mut b2) = RefMut::map_split(x.borrow_mut(), |slc| slc.split_at_mut(1));
+        assert_eq!(*b1, [1]);
+        assert_eq!(*b2, [2]);
+        b1[0] = 2;
+        b2[0] = 1;
+    }
+    assert_eq!(*x.borrow(), [2, 1]);
+}
+
+#[test]
 fn ref_map_accessor() {
     struct X(RefCell<(u32, char)>);
     impl X {
diff --git a/src/libcore/tests/lib.rs b/src/libcore/tests/lib.rs
index 11765e3ef56..87612b7e818 100644
--- a/src/libcore/tests/lib.rs
+++ b/src/libcore/tests/lib.rs
@@ -27,6 +27,7 @@
 #![feature(pattern)]
 #![feature(range_is_empty)]
 #![feature(raw)]
+#![feature(refcell_map_split)]
 #![feature(refcell_replace_swap)]
 #![feature(slice_patterns)]
 #![feature(slice_rotate)]