mascai
mascai

Reputation: 1872

Expected struct `ListNode`, found `&mut ListNode`

I am writing a custom linked list in Rust. I have implemented push_front() function and want to reuse it in insert() function

I have an error: > expected struct ListNode, found &mut ListNode

#[derive(Eq, PartialEq, Clone, Debug)]
struct ListNode {
    val: i32,
    next: Option<Box<ListNode>>
}
impl ListNode {
    fn new(val: i32) -> Self {
        println!("Call new {}", val);
        return ListNode {
            val: val,
            next: None
        };
    }

    fn push_front(self, mut new_head: Option<Box<ListNode>>) -> Option<Box<ListNode>> {
        new_head.as_mut().unwrap().next = Some(Box::new(self));
        return new_head;
    }

    fn insert(&mut self, new_node: Option<Box<ListNode>>, insert_pos: i32) {
        if insert_pos == 0 {
            self = Self::push_front(self, new_node).as_mut().unwrap(); // ERROR expected struct `ListNode`, found `&mut ListNode`
        }
    }
}

How can I fix the error?

Upvotes: 0

Views: 128

Answers (1)

Fomalhaut
Fomalhaut

Reputation: 9825

Since you are implementing a linked list, I would suggest you to consider a different interface and the way you are going to use it, to access the elements and so on. Remember, Rust has ownership-borrowing feature so you are not allowed to access the saved nodes from any piece of your code. Once you borrowed a node to the next field, you'll no longer work with it normally. So I think in your task you may try this use case:

fn main() {
    let mut n1 = ListNode::new(5);
    let mut n2 = ListNode::new(15);
    let mut n3 = ListNode::new(8);

    n1.push_back(n2);
    n1.get_next().push_back(n3);  // Or even n3.push_back(n1); but print n3 instead below

    println!("{:?}", n1);
    // println!("{:?}", n2);  // Error because n2 is borrowed
    println!("{:?}", n1.get_next().get_next());
}

To make it work this way, the implementation seems to be much easier than you posted:

#[derive(Debug)]
struct ListNode {
    pub val: i32,
    pub next: Option<Box<ListNode>>,
}


impl ListNode {
    fn new(val: i32) -> Self {
        Self {
            val,
            next: None,
        }
    }

    fn push_back(&mut self, node: Self) {
        self.next = Some(Box::new(node));
    }

    fn get_next(&mut self) -> &mut Box<Self> {
        self.next.as_mut().unwrap()
    }
}

Enjoy.

Upvotes: 1

Related Questions