Skip to content

Matches on &mut[] move the .. match & don't consider disjointness #8636

@huonw

Description

@huonw

I believe the following should work, since head and tail are disjoint, and tail is just taking a slice into v (this would mean that v is inaccessible while the result of mut_head_tail is kept around):

fn mut_head_tail<'a, A>(v: &'a mut [A]) -> Option<(&'a mut A, &'a mut [A])> { match v { [ref mut head, .. tail] => { Some((head, tail)) } [] => None } /* // this works currently:  if v.is_empty() {  None  } else {  let (low, hi) = v.mut_split(1);  Some((&mut low[0], hi))  }  */ } fn main() { let mut v = ~[1,2,3,4]; match mut_head_tail(v) { None => {}, Some((h,t)) => { *h = 1000; t.reverse(); } } println!("{:?}", v); }
mut-vec-match.rs:3:26: 3:30 error: cannot bind by-move and by-ref in the same pattern mut-vec-match.rs:3 [ref mut head, .. tail] => { ^~~~ mut-vec-match.rs:3:9: 3:21 note: by-ref binding occurs here mut-vec-match.rs:3 [ref mut head, .. tail] => { ^~~~~~~~~~~~ error: aborting due to previous error 

Changing it to (and removing the t.reverse()):

fn mut_head_tail<'a, A>(v: &'a mut [A]) -> Option<(&'a mut A, ())> { match v { [ref mut head, .. ref mut _tail] => { Some((head, ())) } [] => None } }
mut-vec-match.rs:21:9: 21:21 error: cannot borrow `(*v)[]` as mutable more than once at a time mut-vec-match.rs:21 [ref mut head, .. ref mut _tail] => { ^~~~~~~~~~~~ mut-vec-match.rs:21:8: 21:40 note: second borrow of `(*v)[]` as mutable occurs here mut-vec-match.rs:21 [ref mut head, .. ref mut _tail] => { ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ error: aborting due to previous error 

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-borrow-checkerArea: The borrow checkerC-enhancementCategory: An issue proposing an enhancement or a PR with one.fixed-by-NLLBugs fixed, but only when NLL is enabled.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions