about summary refs log tree commit diff
path: root/src/test/ui/or-patterns
diff options
context:
space:
mode:
authorMatthew Jasper <mjjasper1@gmail.com>2019-12-27 18:11:20 +0000
committerMatthew Jasper <mjjasper1@gmail.com>2020-02-03 19:42:15 +0000
commitc7e6f88926e746d310ca15ce9761b3fd434dbfd2 (patch)
tree1210207aad7df05c0dba9044d2bebf03e6f27073 /src/test/ui/or-patterns
parent0b1ff27cd8968454771d419703873e3f98caf2eb (diff)
downloadrust-c7e6f88926e746d310ca15ce9761b3fd434dbfd2.tar.gz
rust-c7e6f88926e746d310ca15ce9761b3fd434dbfd2.zip
Add more tests for or-patterns
Diffstat (limited to 'src/test/ui/or-patterns')
-rw-r--r--src/test/ui/or-patterns/bindings-runpass-1.rs25
-rw-r--r--src/test/ui/or-patterns/bindings-runpass-2.rs32
-rw-r--r--src/test/ui/or-patterns/for-loop.rs18
-rw-r--r--src/test/ui/or-patterns/if-let-while-let.rs22
-rw-r--r--src/test/ui/or-patterns/issue-67514-irrefutable-param.rs11
-rw-r--r--src/test/ui/or-patterns/let-pattern.rs19
-rw-r--r--src/test/ui/or-patterns/search-via-bindings.rs66
7 files changed, 193 insertions, 0 deletions
diff --git a/src/test/ui/or-patterns/bindings-runpass-1.rs b/src/test/ui/or-patterns/bindings-runpass-1.rs
new file mode 100644
index 00000000000..0087167af7e
--- /dev/null
+++ b/src/test/ui/or-patterns/bindings-runpass-1.rs
@@ -0,0 +1,25 @@
+// run-pass
+
+#![feature(or_patterns)]
+
+fn two_bindings(x: &((bool, bool), u8)) -> u8 {
+    match x {
+        &((true, y) | (y, true), z @ (0 | 4)) => (y as u8) + z,
+        _ => 20,
+    }
+}
+
+fn main() {
+    assert_eq!(two_bindings(&((false, false), 0)), 20);
+    assert_eq!(two_bindings(&((false, true), 0)), 0);
+    assert_eq!(two_bindings(&((true, false), 0)), 0);
+    assert_eq!(two_bindings(&((true, true), 0)), 1);
+    assert_eq!(two_bindings(&((false, false), 4)), 20);
+    assert_eq!(two_bindings(&((false, true), 4)), 4);
+    assert_eq!(two_bindings(&((true, false), 4)), 4);
+    assert_eq!(two_bindings(&((true, true), 4)), 5);
+    assert_eq!(two_bindings(&((false, false), 3)), 20);
+    assert_eq!(two_bindings(&((false, true), 3)), 20);
+    assert_eq!(two_bindings(&((true, false), 3)), 20);
+    assert_eq!(two_bindings(&((true, true), 3)), 20);
+}
diff --git a/src/test/ui/or-patterns/bindings-runpass-2.rs b/src/test/ui/or-patterns/bindings-runpass-2.rs
new file mode 100644
index 00000000000..0e1eb7b2e03
--- /dev/null
+++ b/src/test/ui/or-patterns/bindings-runpass-2.rs
@@ -0,0 +1,32 @@
+// run-pass
+
+#![feature(or_patterns)]
+
+fn or_at(x: Result<u32, u32>) -> u32 {
+    match x {
+        Ok(x @ 4) | Err(x @ (6 | 8)) => x,
+        Ok(x @ 1 | x @ 2) => x,
+        Err(x @ (0..=10 | 30..=40)) if x % 2 == 0 => x + 100,
+        Err(x @ 0..=40) => x + 200,
+        _ => 500,
+    }
+}
+
+fn main() {
+    assert_eq!(or_at(Ok(1)), 1);
+    assert_eq!(or_at(Ok(2)), 2);
+    assert_eq!(or_at(Ok(3)), 500);
+    assert_eq!(or_at(Ok(4)), 4);
+    assert_eq!(or_at(Ok(5)), 500);
+    assert_eq!(or_at(Ok(6)), 500);
+    assert_eq!(or_at(Err(1)), 201);
+    assert_eq!(or_at(Err(2)), 102);
+    assert_eq!(or_at(Err(3)), 203);
+    assert_eq!(or_at(Err(4)), 104);
+    assert_eq!(or_at(Err(5)), 205);
+    assert_eq!(or_at(Err(6)), 6);
+    assert_eq!(or_at(Err(7)), 207);
+    assert_eq!(or_at(Err(8)), 8);
+    assert_eq!(or_at(Err(20)), 220);
+    assert_eq!(or_at(Err(50)), 500);
+}
diff --git a/src/test/ui/or-patterns/for-loop.rs b/src/test/ui/or-patterns/for-loop.rs
new file mode 100644
index 00000000000..b79af6c402e
--- /dev/null
+++ b/src/test/ui/or-patterns/for-loop.rs
@@ -0,0 +1,18 @@
+// Check that or patterns are lowered correctly in `for` loops.
+// run-pass
+
+#![feature(or_patterns)]
+
+fn main() {
+    let v = vec![Ok(2), Err(3), Ok(5)];
+    let mut w = Vec::new();
+    for &(Ok(i) | Err(i)) in &v {
+        w.push(i);
+    }
+    let mut u = Vec::new();
+    for Ok(i) | Err(i) in v {
+        u.push(i);
+    }
+    assert_eq!(w, [2, 3, 5]);
+    assert_eq!(u, [2, 3, 5]);
+}
diff --git a/src/test/ui/or-patterns/if-let-while-let.rs b/src/test/ui/or-patterns/if-let-while-let.rs
new file mode 100644
index 00000000000..9256360b29d
--- /dev/null
+++ b/src/test/ui/or-patterns/if-let-while-let.rs
@@ -0,0 +1,22 @@
+// Check that or patterns are lowered correctly in `if let` and `while let` expressions.
+// run-pass
+
+#![feature(or_patterns)]
+
+fn main() {
+    let mut opt = Some(3);
+    let mut w = Vec::new();
+    while let Some(ref mut val @ (3 | 4 | 6)) = opt {
+        w.push(*val);
+        *val += 1;
+    }
+    assert_eq!(w, [3, 4]);
+    if let &(None | Some(6 | 7)) = &opt {
+        unreachable!();
+    }
+    if let Some(x @ (4 | 5 | 6)) = opt {
+        assert_eq!(x, 5);
+    } else {
+        unreachable!();
+    }
+}
diff --git a/src/test/ui/or-patterns/issue-67514-irrefutable-param.rs b/src/test/ui/or-patterns/issue-67514-irrefutable-param.rs
new file mode 100644
index 00000000000..0c2ae44e546
--- /dev/null
+++ b/src/test/ui/or-patterns/issue-67514-irrefutable-param.rs
@@ -0,0 +1,11 @@
+// Check that we don't ICE for irrefutable or-patterns in function parameters
+
+// check-pass
+
+#![feature(or_patterns)]
+
+fn foo((Some(_) | None): Option<u32>) {}
+
+fn main() {
+    foo(None);
+}
diff --git a/src/test/ui/or-patterns/let-pattern.rs b/src/test/ui/or-patterns/let-pattern.rs
new file mode 100644
index 00000000000..07e37412ce8
--- /dev/null
+++ b/src/test/ui/or-patterns/let-pattern.rs
@@ -0,0 +1,19 @@
+#![feature(or_patterns)]
+
+// run-pass
+
+fn or_pat_let(x: Result<u32, u32>) -> u32 {
+    let Ok(y) | Err(y) = x;
+    y
+}
+
+fn or_pat_arg((Ok(y) | Err(y)): Result<u32, u32>) -> u32 {
+    y
+}
+
+fn main() {
+    assert_eq!(or_pat_let(Ok(3)), 3);
+    assert_eq!(or_pat_let(Err(5)), 5);
+    assert_eq!(or_pat_arg(Ok(7)), 7);
+    assert_eq!(or_pat_arg(Err(9)), 9);
+}
diff --git a/src/test/ui/or-patterns/search-via-bindings.rs b/src/test/ui/or-patterns/search-via-bindings.rs
new file mode 100644
index 00000000000..eb127b881cd
--- /dev/null
+++ b/src/test/ui/or-patterns/search-via-bindings.rs
@@ -0,0 +1,66 @@
+// Check that we expand multiple or-patterns from left to right.
+
+// run-pass
+
+#![feature(or_patterns)]
+#![allow(unreachable_patterns)] // FIXME(or-patterns) this shouldn't trigger
+
+fn search(target: (bool, bool, bool)) -> u32 {
+    let x = ((false, true), (false, true), (false, true));
+    let mut guard_count = 0;
+    match x {
+        ((a, _) | (_, a), (b @ _, _) | (_, b @ _), (c @ false, _) | (_, c @ true))
+            if {
+                guard_count += 1;
+                (a, b, c) == target
+            } =>
+        {
+            guard_count
+        }
+        _ => unreachable!(),
+    }
+}
+
+// Equivalent to the above code, but hopefully easier to understand.
+fn search_old_style(target: (bool, bool, bool)) -> u32 {
+    let x = ((false, true), (false, true), (false, true));
+    let mut guard_count = 0;
+    match x {
+        ((a, _), (b @ _, _), (c @ false, _))
+        | ((a, _), (b @ _, _), (_, c @ true))
+        | ((a, _), (_, b @ _), (c @ false, _))
+        | ((a, _), (_, b @ _), (_, c @ true))
+        | ((_, a), (b @ _, _), (c @ false, _))
+        | ((_, a), (b @ _, _), (_, c @ true))
+        | ((_, a), (_, b @ _), (c @ false, _))
+        | ((_, a), (_, b @ _), (_, c @ true))
+            if {
+                guard_count += 1;
+                (a, b, c) == target
+            } =>
+        {
+            guard_count
+        }
+        _ => unreachable!(),
+    }
+}
+
+fn main() {
+    assert_eq!(search((false, false, false)), 1);
+    assert_eq!(search((false, false, true)), 2);
+    assert_eq!(search((false, true, false)), 3);
+    assert_eq!(search((false, true, true)), 4);
+    assert_eq!(search((true, false, false)), 5);
+    assert_eq!(search((true, false, true)), 6);
+    assert_eq!(search((true, true, false)), 7);
+    assert_eq!(search((true, true, true)), 8);
+
+    assert_eq!(search_old_style((false, false, false)), 1);
+    assert_eq!(search_old_style((false, false, true)), 2);
+    assert_eq!(search_old_style((false, true, false)), 3);
+    assert_eq!(search_old_style((false, true, true)), 4);
+    assert_eq!(search_old_style((true, false, false)), 5);
+    assert_eq!(search_old_style((true, false, true)), 6);
+    assert_eq!(search_old_style((true, true, false)), 7);
+    assert_eq!(search_old_style((true, true, true)), 8);
+}