Rust: вывести значение из опциона и поместить в стек - PullRequest
0 голосов
/ 09 апреля 2020

У меня есть значение типа Option. Если в типе есть значение Leg, я хочу изменить структуру Leg, а затем пометить ее как «завершенную», переместив этап из того места, где он хранится в self._current_leg, в стек завершенных участков в self._completed_legs. , Затем я хочу установить значение _current_leg для следующего этапа в стеке _expected_legs. Тем не менее, я получаю ошибку несоответствующего типа в строке self._completed_legs.push(leg) в Trip.dropoff(), потому что стек ожидает структуру типа Leg, и я передаю тип &mut Leg. Я не знаю, как переместить значение из переменной _current_leg - кажется, я могу заимствовать только значение.

Соответствующий код находится внизу этого блока кода. Спасибо за помощь.

use std::collections;

pub struct Stack<T> {
    maxsize: usize,
    items: Vec<T>,
}

impl<T> Stack<T> {

    pub fn new(maxsize: usize) -> Self {
        Self {
            maxsize,
            items: Vec::with_capacity(maxsize),
        }
    }
    pub fn pop(&mut self) -> Option<T> {
        self.items.pop()
    }
    pub fn push(&mut self, item: T) -> bool {
        if self.items.len() == self.maxsize {
            return false;
        }
        self.items.push(item);
        return true;
    }
    pub fn size(&self) -> usize {
        self.items.len()
    }
    pub fn peek(&self) -> Option<&T> {
        self.items.last()
    }
}

pub struct Leg {
    // not important
    _trip_index: usize
}

impl Leg {
    fn dropoff(&mut self, time: i64) {

    }

    fn pickup(&mut self, time: i64) {

    }
}

pub struct Trip {
    _current_leg: Option<Leg>,
    _completed_legs: Stack<Leg>,
    _expected_legs: Stack<Leg>
}

impl Trip {

    fn dropoff(&mut self, time: i64) {
        let leg = self._current_leg.as_mut().unwrap();
        leg.dropoff(time);
        self._completed_legs.push(leg);
        self._current_leg = self._expected_legs.pop();
    }
}

1 Ответ

1 голос
/ 09 апреля 2020

Ваш self._current_leg относится к типу Option<Leg>, но вы не можете владеть им, потому что он является частью self. В основном, как если бы у вас был &mut Option<Leg>. Вы не можете звонить unwrap(), так как unwrap() становится владельцем Option.

Вы решили этот вызов as_mut(), но это преобразует ваш &mut Option<Leg> в Option<&mut Leg>: теперь вы владеете Option, но оно не содержит значения, это просто ссылка, поэтому вы все еще не владеете Leg.

Вам нужно Option::take():

pub fn take(&mut self) -> Option<T>

Он заменит данное значение на None и вернет предыдущее значение. Примерно так будет работать в вашем коде:

let mut leg = self._current_leg.take().unwrap();
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...