As a training project for Rust, I have a very simple (working, if not complete) implementation of a singly linked list. Declaration of structures is as follows:
type NodePtr<T> = Option<Box<Node<T>>>; struct Node<T> { data: T, next: NodePtr<T>, } pub struct LinkedList<T> { head: NodePtr<T>, }
The implementation of size and push_front were fairly straightforward, although size was iteratively related to some โborrower strugglesโ.
The next thing I wanted to try was to add a tail pointer to the LinkedList structure. for effective work push_back . Here I came across a wall. First I tried to use Option<&Box<Node<T>>> , and then Option<&Node<T>> . Both of them led to the fact that they were strewn down everywhere, but still could not promise that the check of the lifetime would be tail .
Since then, I have come to the preliminary conclusion that with these definitions it is impossible: there is no way to guarantee to the compiler that tail will be valid in those places that I think are valid. The only way I can do this is to have all my pointers be Rc<_> or Rc<RefCell<_>> , because these are the only safe ways to have two things pointing to the same object (final node).
My question is: is this the correct conclusion? More generally: what is the idiomatic Rust solution for unpublished pointers inside data structures? In my opinion, link counting seems terribly difficult for something so simple, so I think I'm missing something. (Or maybe I haven't gotten to the right mindset for memory security.)
source share