Difficult borrowing situation


#1

Hello,

I’m trying to remove an element from a vec with the new remove_item method.
To do so, I loop through the vec to obtain the reference I’m searching for and I then use it to call remove_item.
Sadly, I can’t make it work.

Take a look at this demo: https://play.rust-lang.org/?gist=0b160bb354a2798460b3db54db8ecc30&version=nightly

Thanks a lot for your help.
Jean-Sébastien


#2

This way of working is inherently incompatible with Rust, because you’re holding on to a read-only reference that “freezes” the object it belongs to for as long as the reference exists. Don’t think of references as pointers to elements, but as read/write locks on data.

It’s also inefficient, because remove_item searches again.

You can use .iter().enumerate() and remember the index to remove. This will enable most efficient removal, and the index will go under the radar of the borrow checker.

If you were combining this with other iterators or .collect(), use .filter() instead.


#3

drain_filter() is probably a better way to go.


#4

drain_filter would be ideal for this, but unfortunately it’s dead.


#5

Hmm, ok. I didn’t read the issue thoroughly but it sounds like something else like it might surface in the future.


#6

Thanks for your response, after one day on this problem, I understand that I have to use another way to fix my problem.


#7

The most straightforward (and stable channel) approach is a one-liner:

lock.iter().position(|&x| x == 10).map(|p| lock.remove(p));