BacCM
@BacCM
C++ почти с рождения

Как передать в функцию ссылки на два элемента вектора?

Раст только начал щупать. И естественно всякие непонятки с поведением "borrowed content".

Вот, например, есть вектор структур, и я хочу что-то сделать с содержимым нескольких элементов этого вектора.
Передаю в функцию мутабельные ссылки. И получаю:

131 |     foo(&mut v[0], &mut v[1]);
    |     ---      -          ^ second mutable borrow occurs here
    |     |        |
    |     |        first mutable borrow occurs here
    |     first borrow later used by call


Для пробы я попробовал вызов для пары обычных переменных на стеке. Всё ожидаемо работает.
Есть обходной манёвр с двойным копированием, который дико выглядит.
Кстати почему не компилируется?
let mut va : P = v[0];
Обязательно требуется клонирование

Собственно код, тут сразу все три варианта...
#[derive(Debug, Clone)]
struct P {
	x : i32,
	y : i32
}

fn foo(a : &mut P, b : &mut P) 
{
	a.x = b.x + 1;
	b.y = a.y + 1;
}

fn main() 
{
// Это ожидаемо работает
	let mut a = P{x:1, y:2};
	let mut b = P{x:10, y:20};
	
	foo(&mut a, &mut b);

	println!("{:?} {:?}", a, b);

	let mut v : Vec<P> = [
			P{x:1, y:2}, 
			P{x:10, y:20}
		].to_vec();

// А это уже нет !!!
//	foo(&mut v[0], &mut v[1]);   


// Так можно "обойти",  но это явно не то ради чего придумывался rust
	let mut va : P = v[0].clone();
	let mut vb : P = v[1].clone();

	foo(&mut va, &mut vb);

	v[0] = va;
	v[1] = vb;

	println!("{:?}", v);
}
  • Вопрос задан
  • 199 просмотров
Решения вопроса 1
ozkriff
@ozkriff
Rust э̶н̶т̶у̶з̶и̶а̶с̶т сектант, хобби игродел
https://stackoverflow.com/questions/30073684/how-t...

TLDR: ты хочешь https://doc.rust-lang.org/std/primitive.slice.html... потому что Ржавчина разрешает иметь только одну активную изменяющую ссылку на сущность, а знание о том, как устроен срез/вектор в язык не зашито, т.е. это решается функциями с unsafe внутри.
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
@inv2004
Именно в коде как вы написали, и как передаёте в функцию, это скорее выглядит как кортеж:
let mut v = (P{x:1, y:2}, P{x:10, y:20});

в данном случае всё бы работало.
Если это всё же вектор, то раст должен знать как работает вектор чтобы гарантировать отсутствие проблем при наличии двойной мутабельной ссылки.
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы