@@ -1506,6 +1506,128 @@ impl<'a, T> CursorMut<'a, T> {
1506
1506
self . index = 0 ;
1507
1507
unsafe { self . list . split_off_before_node ( self . current , split_off_idx) }
1508
1508
}
1509
+
1510
+ /// Appends an element to the front of the cursor's parent list. The node
1511
+ /// that the cursor points to is unchanged, even if it is the "ghost" node.
1512
+ ///
1513
+ /// This operation should compute in O(1) time.
1514
+ // `push_front` continues to point to "ghost" when it addes a node to mimic
1515
+ // the behavior of `insert_before` on an empty list.
1516
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1517
+ pub fn push_front ( & mut self , elt : T ) {
1518
+ // Safety: We know that `push_front` does not change the position in
1519
+ // memory of other nodes. This ensures that `self.current` remains
1520
+ // valid.
1521
+ self . list . push_front ( elt) ;
1522
+ self . index += 1 ;
1523
+ }
1524
+
1525
+ /// Appends an element to the back of the cursor's parent list. The node
1526
+ /// that the cursor points to is unchanged, even if it is the "ghost" node.
1527
+ ///
1528
+ /// This operation should compute in O(1) time.
1529
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1530
+ pub fn push_back ( & mut self , elt : T ) {
1531
+ // Safety: We know that `push_back` does not change the position in
1532
+ // memory of other nodes. This ensures that `self.current` remains
1533
+ // valid.
1534
+ self . list . push_back ( elt) ;
1535
+ }
1536
+
1537
+ /// Removes the first element from the cursor's parent list and returns it,
1538
+ /// or None if the list is empty. The element the cursor points to remains
1539
+ /// unchanged, unless it was pointing to the front element. In that case, it
1540
+ /// points to the new front element.
1541
+ ///
1542
+ /// This operation should compute in O(1) time.
1543
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1544
+ pub fn pop_front ( & mut self ) -> Option < T > {
1545
+ // We can't check if current is empty, we must check the list directly.
1546
+ // It is possible for `self.current == None` and the list to be
1547
+ // non-empty.
1548
+ if self . list . is_empty ( ) {
1549
+ None
1550
+ } else {
1551
+ // We can't point to the node that we pop. Copying the behavior of
1552
+ // `remove_current`, we move on the the next node in the sequence.
1553
+ // If the list is of length 1 then we end pointing to the "ghost"
1554
+ // node, which is expected.
1555
+ if self . list . head == self . current {
1556
+ self . move_next ( ) ;
1557
+ }
1558
+ // We always need to change the index since `head` comes before any
1559
+ // other element.
1560
+ self . index . checked_sub ( 1 ) . unwrap_or ( 0 ) ;
1561
+ self . list . pop_front ( )
1562
+ }
1563
+ }
1564
+
1565
+ /// Removes the last element from the cursor's parent list and returns it,
1566
+ /// or None if the list is empty. The element the cursor points to remains
1567
+ /// unchanged, unless it was pointing to the back element. In that case, it
1568
+ /// points to the new back element.
1569
+ ///
1570
+ /// This operation should compute in O(1) time.
1571
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1572
+ pub fn pop_back ( & mut self ) -> Option < T > {
1573
+ if self . list . is_empty ( ) {
1574
+ None
1575
+ } else {
1576
+ if self . list . tail == self . current {
1577
+ self . move_prev ( )
1578
+ }
1579
+ // We don't need to change the index since `current` points to a
1580
+ // node before `tail`.
1581
+ self . list . pop_back ( )
1582
+ }
1583
+ }
1584
+
1585
+ /// Provides a reference to the front element of the cursor's parent list,
1586
+ /// or None if the list is empty.
1587
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1588
+ pub fn front ( & self ) -> Option < & T > {
1589
+ self . list . front ( )
1590
+ }
1591
+
1592
+ /// Provides a mutable reference to the front element of the cursor's
1593
+ /// parent list, or None if the list is empty.
1594
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1595
+ pub fn front_mut ( & mut self ) -> Option < & mut T > {
1596
+ self . list . front_mut ( )
1597
+ }
1598
+
1599
+ /// Provides a reference to the back element of the cursor's parent list,
1600
+ /// or None if the list is empty.
1601
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1602
+ pub fn back ( & self ) -> Option < & T > {
1603
+ self . list . back ( )
1604
+ }
1605
+
1606
+ /// Provides a mutable reference to back element of the cursor's parent
1607
+ /// list, or `None` if the list is empty.
1608
+ ///
1609
+ /// # Examples
1610
+ /// Building and mutating a list with a cursor, then getting the back element:
1611
+ /// ```
1612
+ /// #![feature(linked_list_cursors)]
1613
+ /// use std::collections::LinkedList;
1614
+ /// let mut dl = LinkedList::new();
1615
+ /// dl.push_front(3);
1616
+ /// dl.push_front(2);
1617
+ /// dl.push_front(1);
1618
+ /// let mut cursor = dl.cursor_front_mut();
1619
+ /// *cursor.current().unwrap() = 99;
1620
+ /// *cursor.back_mut().unwrap() = 0;
1621
+ /// let mut contents = dl.into_iter();
1622
+ /// assert_eq!(contents.next(), Some(99));
1623
+ /// assert_eq!(contents.next(), Some(2));
1624
+ /// assert_eq!(contents.next(), Some(0));
1625
+ /// assert_eq!(contents.next(), None);
1626
+ /// ```
1627
+ #[ unstable( feature = "linked_list_cursors" , issue = "58533" ) ]
1628
+ pub fn back_mut ( & mut self ) -> Option < & mut T > {
1629
+ self . list . back_mut ( )
1630
+ }
1509
1631
}
1510
1632
1511
1633
/// An iterator produced by calling `drain_filter` on LinkedList.
0 commit comments