array_linked_list/lib.rs
1#![deny(missing_docs)]
2
3/*!
4The `ArrayLinkedList` data structure combines the benefit of an array and a linked list.
5
6Every supported operation, which does not (re-)allocate the array, is done in *O*(1):
7
8* inserting elements at the front and back
9* popping element at the front or back
10* getting the element count
11* removing elements at an arbitrary index
12* inserting elements at an arbitrary index
13* replacing elements at an arbitrary index
14
15It's stored like an array, but contains some additional information.
16
17You would typically use it, where you need to be able to do multiple of the following tasks efficiently:
18
19* accessing single elements by index
20* adding and removing elements without changing order or indices
21* sorting elements without changing indices or moving the content around.
22
23# Order and indexing
24
25You might also use it as a more convenient version of a `Vec<Option<T>>`.
26When iterating over it, only the elements, which are `Some` are given to the user.
27And even the checks for `Some` are optimized away.
28So when it's likely, that most of the options of a large array are `None`, this might be a huge performance improvement.
29
30Another advantage over a `LinkedList` is the cache locality.
31Everything is laid out in a contiguous region of memory.
32Compared to a `Vec` on the other hand, it might be bad.
33The iteration does not necessarily take place in the same order.
34That's mostly a problem for large arrays.
35The iterator would jump back and forth in the array.
36
37In order to understand this type, it's necessary to know about the iteration order.
38There is a logical order, which is used by the iterators, or when doing anything with the first and last elements.
39You can think of it as the order of a linked list, which is just packed into an array here.
40And then there is indexing, which has nothing to do with the order of the linked list.
41The indices just return the array elements.
42
43## Index Example
44
45So when adding an element to the linked array without specifying the index, you get the index, it was put to, as a result.
46The results are always added to the array in order, so the indices increase, no matter if you add the indices to the front or to the back:
47
48```
49use array_linked_list::ArrayLinkedList;
50
51let mut array = ArrayLinkedList::new();
52
53assert_eq!(array.push_front(1), 0);
54assert_eq!(array.push_back(2), 1);
55assert_eq!(array.push_front(3), 2);
56assert_eq!(array.push_front(4), 3);
57assert_eq!(array.push_back(5), 4);
58```
59
60## Order example
61
62When you just apped elements from the front or back, the indices even correlate to the order:
63
64```
65use array_linked_list::ArrayLinkedList;
66
67let mut array = ArrayLinkedList::new();
68
69array.push_front(1);
70array.push_front(2);
71array.push_front(3);
72
73for (i, element) in array.iter().rev().enumerate() {
74 assert_eq!(*element, array[i].unwrap());
75}
76```
77
78```
79use array_linked_list::ArrayLinkedList;
80
81let mut array = ArrayLinkedList::new();
82
83array.push_back(1);
84array.push_back(2);
85array.push_back(3);
86
87for (i, element) in array.iter().enumerate() {
88 assert_eq!(*element, array[i].unwrap());
89}
90```
91
92## Iteration over unsorted lists
93
94In realistic cases, you need to store the indices somewhere else, if you need them.
95Alternatively, you can also use
96
97```
98use array_linked_list::ArrayLinkedList;
99
100let mut array = ArrayLinkedList::new();
101
102array.push_back(1);
103array.push_front(2);
104array.push_front(3);
105array.push_back(4);
106array.push_front(5);
107
108for (index, element) in array.indexed().rev() {
109 assert_eq!(*element, array[index].unwrap());
110}
111```
112
113## Conclusion
114
115Just remember, that indices and order are two different things, which don't correlate, and you should be safe.
116
117**/
118
119use std::{
120 mem,
121 ops::{Index, IndexMut},
122};
123
124#[derive(Copy, Clone, Debug)]
125struct LinkedListNode<T> {
126 next_index: usize,
127 prev_index: usize,
128 data: Option<T>,
129}
130
131impl<T> LinkedListNode<T> {
132 fn new(prev_index: usize, next_index: usize, data: T) -> Self {
133 Self {
134 next_index,
135 prev_index,
136 data: Some(data),
137 }
138 }
139
140 fn front(first_index: usize, data: T) -> Self {
141 Self {
142 next_index: first_index,
143 prev_index: 0,
144 data: Some(data),
145 }
146 }
147
148 fn back(last_index: usize, data: T) -> Self {
149 Self {
150 next_index: 0,
151 prev_index: last_index,
152 data: Some(data),
153 }
154 }
155
156 fn deleted(free_index: usize) -> Self {
157 Self {
158 next_index: free_index,
159 prev_index: 0,
160 data: None,
161 }
162 }
163}
164
165/// The `ArrayLinkedList` type, which combines the advantages of dynamic arrays and linked lists.
166#[derive(Clone, Debug, Default)]
167pub struct ArrayLinkedList<T> {
168 count: usize,
169 first_index: usize,
170 last_index: usize,
171 free_index: usize,
172 end_index: usize,
173 elements: Vec<LinkedListNode<T>>,
174}
175
176impl<T> ArrayLinkedList<T> {
177 /// Constructs a new, empty `ArrayLinkedList`.
178 ///
179 /// The linked array will not allocate until elements are pushed onto it.
180 pub fn new() -> Self {
181 Self {
182 count: 0,
183 first_index: 0,
184 last_index: 0,
185 free_index: 0,
186 end_index: 0,
187 elements: Vec::new(),
188 }
189 }
190
191 #[inline]
192 fn fill_elements(&mut self, capacity: usize) {
193 if capacity == 0 {
194 return;
195 }
196 for i in 1..capacity {
197 self.elements.push(LinkedListNode::deleted(i + 1))
198 }
199 self.elements.push(LinkedListNode::deleted(0));
200
201 self.free_index = 1;
202 self.end_index = capacity;
203 }
204
205 /// Constructs a new, empty `ArrayLinkedList<T>` with the specified capacity.
206 ///
207 /// The array will be able to hold exactly `capacity` elements without reallocating.
208 // If `capacity` is 0, the vector will not allocate.
209 pub fn with_capacity(capacity: usize) -> Self {
210 let mut result = Self::new();
211 result.elements = Vec::with_capacity(capacity);
212 result.fill_elements(capacity);
213 result
214 }
215
216 fn insert_free_element(&mut self, element: LinkedListNode<T>) -> usize {
217 if self.free_index == 0 {
218 self.elements.push(element);
219 self.elements.len()
220 } else {
221 let free_index = self.free_index;
222 let recycle_element = &mut self.elements[free_index - 1];
223 self.free_index = recycle_element.next_index;
224 *recycle_element = element;
225 free_index
226 }
227 }
228
229 /// Adds an element at the front of the array and returns its index.
230 /// The indices are returned in a raising order, starting with zero.
231 /// See the module description for more information.
232 ///
233 /// This operation should compute in *O*(1) time.
234 ///
235 /// # Examples
236 ///
237 /// ```
238 /// use array_linked_list::ArrayLinkedList;
239 ///
240 /// let mut array = ArrayLinkedList::new();
241 ///
242 /// assert_eq!(array.push_front(2), 0);
243 /// assert_eq!(array.front().unwrap(), &2);
244 ///
245 /// assert_eq!(array.push_front(1), 1);
246 /// assert_eq!(array.front().unwrap(), &1);
247 /// ```
248 pub fn push_front(&mut self, value: T) -> usize {
249 let element = LinkedListNode::front(self.first_index, value);
250
251 let next_index = self.insert_free_element(element);
252
253 *self.prev_of_next(self.first_index, true) = next_index;
254
255 self.first_index = next_index;
256 self.count += 1;
257
258 next_index - 1
259 }
260
261 /// Adds an element at the back of the array and returns its index.
262 /// The indices are returned in a raising order, starting with zero.
263 /// See the module description for more information.
264 ///
265 /// This operation should compute in *O*(1) time.
266 ///
267 /// # Examples
268 ///
269 /// ```
270 /// use array_linked_list::ArrayLinkedList;
271 ///
272 /// let mut array = ArrayLinkedList::new();
273 ///
274 /// assert_eq!(array.push_back(1), 0);
275 /// assert_eq!(array.push_back(3), 1);
276 /// assert_eq!(3, *array.back().unwrap());
277 /// ```
278 pub fn push_back(&mut self, value: T) -> usize {
279 let element = LinkedListNode::back(self.last_index, value);
280
281 let prev_index = self.insert_free_element(element);
282
283 *self.next_of_prev(self.last_index, true) = prev_index;
284
285 self.last_index = prev_index;
286 self.count += 1;
287
288 prev_index - 1
289 }
290
291 fn insert_between(&mut self, prev_index: usize, next_index: usize, value: T) -> usize {
292 let element = LinkedListNode::new(prev_index, next_index, value);
293
294 let index = self.insert_free_element(element);
295
296 *self.next_of_prev(prev_index, true) = index;
297 *self.prev_of_next(next_index, true) = index;
298
299 self.count += 1;
300
301 index - 1
302 }
303
304 /// Inserts an element after the element at the specified index.
305 /// Returns the index of the inserted element on success.
306 /// If no element was found at the specified index, `None` is returned.
307 ///
308 /// # Panics
309 ///
310 /// Panics if `prev_index >= capacity`
311 ///
312 /// # Examples
313 ///
314 /// ```
315 /// use array_linked_list::ArrayLinkedList;
316 ///
317 /// let mut array = ArrayLinkedList::new();
318 ///
319 /// let first = array.push_back(1);
320 /// let second = array.push_back(2);
321 /// let third = array.push_back(3);
322 ///
323 /// array.insert_after(second, 100);
324 ///
325 /// assert_eq!(array.pop_front(), Some(1));
326 /// assert_eq!(array.pop_front(), Some(2));
327 /// assert_eq!(array.pop_front(), Some(100));
328 /// assert_eq!(array.pop_front(), Some(3));
329 /// assert_eq!(array.pop_front(), None);
330 /// ```
331 pub fn insert_after(&mut self, prev_index: usize, value: T) -> Option<usize> {
332 let LinkedListNode {
333 next_index, data, ..
334 } = &self.elements[prev_index];
335
336 if data.is_some() {
337 let next_index = *next_index;
338 Some(self.insert_between(prev_index + 1, next_index, value))
339 } else {
340 None
341 }
342 }
343
344 /// Inserts an element before the element at the specified index.
345 /// Returns the index of the inserted element on success.
346 /// If no element was found at the specified index, `None` is returned.
347 ///
348 /// # Panics
349 ///
350 /// Panics if `next_index >= capacity`
351 ///
352 /// # Examples
353 ///
354 /// ```
355 /// use array_linked_list::ArrayLinkedList;
356 ///
357 /// let mut array = ArrayLinkedList::new();
358 ///
359 /// let first = array.push_back(1);
360 /// let second = array.push_back(2);
361 /// let third = array.push_back(3);
362 ///
363 /// array.insert_before(second, 100);
364 ///
365 /// assert_eq!(array.pop_front(), Some(1));
366 /// assert_eq!(array.pop_front(), Some(100));
367 /// assert_eq!(array.pop_front(), Some(2));
368 /// assert_eq!(array.pop_front(), Some(3));
369 /// assert_eq!(array.pop_front(), None);
370 /// ```
371 pub fn insert_before(&mut self, next_index: usize, value: T) -> Option<usize> {
372 let LinkedListNode {
373 prev_index, data, ..
374 } = &self.elements[next_index];
375
376 if data.is_some() {
377 let prev_index = *prev_index;
378 Some(self.insert_between(prev_index, next_index + 1, value))
379 } else {
380 None
381 }
382 }
383
384 #[inline]
385 fn prev_of_next(&mut self, index: usize, active: bool) -> &mut usize {
386 if index > 0 {
387 &mut self.elements[index - 1].prev_index
388 } else if active {
389 &mut self.last_index
390 } else {
391 &mut self.end_index
392 }
393 }
394
395 #[inline]
396 fn next_of_prev(&mut self, index: usize, active: bool) -> &mut usize {
397 if index > 0 {
398 &mut self.elements[index - 1].next_index
399 } else if active {
400 &mut self.first_index
401 } else {
402 &mut self.free_index
403 }
404 }
405
406 fn connect_indices(&mut self, prev_index: usize, next_index: usize, active: bool) {
407 *self.prev_of_next(next_index, active) = prev_index;
408 *self.next_of_prev(prev_index, active) = next_index;
409 }
410
411 /// Removes the element at the given index and returns it, or `None` if it is empty.
412 /// The indices of other items are not changed.
413 /// Indices, which have never been used (see `capacity`), will not be available, but panic instead.
414 ///
415 /// Indices are not the position they appear in, when iterating over them.
416 /// So you can't use enumerate to get the index to delete.
417 /// But the iteration order of the elements (in both directions) is preserved.
418 /// See the module description for more information.
419 ///
420 /// This operation should compute in *O*(1) time.
421 ///
422 /// # Panics
423 ///
424 /// Panics if index >= capacity
425 ///
426 /// # Examples
427 ///
428 /// ```
429 /// use array_linked_list::ArrayLinkedList;
430 ///
431 /// let mut array = ArrayLinkedList::new();
432 ///
433 /// let first = array.push_front(1);
434 /// let second = array.push_back(2);
435 /// let third = array.push_front(3);
436 ///
437 ///
438 /// assert_eq!(array.len(), 3);
439 ///
440 /// assert_eq!(array.remove(second).unwrap(), 2);
441 /// assert_eq!(array[second], None);
442 /// assert_eq!(array.len(), 2);
443 /// assert_eq!(array.remove(second), None);
444 /// assert_eq!(array.len(), 2);
445 ///
446 /// assert_eq!(array.remove(first).unwrap(), 1);
447 /// assert_eq!(array.len(), 1);
448 /// assert_eq!(array.remove(third).unwrap(), 3);
449 /// assert_eq!(array.len(), 0);
450 /// assert!(array.is_empty());
451 /// ```
452 pub fn remove(&mut self, index: usize) -> Option<T> {
453 let LinkedListNode {
454 next_index,
455 prev_index,
456 data,
457 } = mem::replace(
458 &mut self.elements[index],
459 LinkedListNode::deleted(self.free_index),
460 );
461
462 let removed = data.is_some();
463 self.connect_indices(prev_index, next_index, removed);
464
465 if removed {
466 self.count -= 1;
467 }
468
469 if self.free_index > 0 {
470 self.elements[self.free_index - 1].prev_index = index + 1;
471 }
472
473 self.free_index = index + 1;
474 data
475 }
476
477 /// Adds element at specified index at the front of the list.
478 /// Useful for updating contents.
479 ///
480 /// It basically does the same as `remove` and `push_back`, even if the specified index is already removed.
481 ///
482 /// # Panics
483 ///
484 /// Panics if index >= capacity
485 ///
486 /// # Examples
487 ///
488 /// ```
489 /// use array_linked_list::ArrayLinkedList;
490 ///
491 /// let mut array = ArrayLinkedList::new();
492 ///
493 /// array.push_front(1);
494 /// let first_index = array.push_back(2);
495 /// array.push_front(3);
496 /// let second_index = array.push_front(4);
497 /// array.push_back(5);
498 ///
499 /// let mut array2 = array.clone();
500 /// for (a, b) in array.iter().zip(&array2) {
501 /// assert_eq!(a, b)
502 /// }
503 ///
504 /// let first_element = array.replace_front(first_index, 100);
505 /// let first_element2 = array2.remove(first_index);
506 /// array2.push_front(100);
507 ///
508 /// assert_eq!(first_element, first_element2);
509 /// for (a, b) in array.iter().zip(&array2) {
510 /// assert_eq!(a, b)
511 /// }
512 ///
513 /// let second_element = array.replace_front(first_index, 0);
514 /// let second_element2 = array2.remove(first_index);
515 /// array2.push_back(0);
516 ///
517 /// assert_eq!(second_element, second_element2);
518 ///
519 /// assert!(array.iter().zip(&array2).any(|(a, b)| a != b));
520 ///
521 /// assert_eq!(array.len(), 5);
522 /// assert_eq!(array2.len(), 5);
523 /// ```
524 pub fn replace_front(&mut self, index: usize, value: T) -> Option<T> {
525 let LinkedListNode {
526 next_index,
527 prev_index,
528 data,
529 } = mem::replace(
530 &mut self.elements[index],
531 LinkedListNode::front(self.first_index, value),
532 );
533
534 let removed = data.is_some();
535 self.connect_indices(prev_index, next_index, removed);
536
537 if !removed {
538 self.count += 1;
539 }
540
541 if self.first_index > 0 {
542 self.elements[self.first_index - 1].prev_index = index + 1;
543 }
544
545 self.first_index = index + 1;
546 data
547 }
548
549 /// Adds element at specified index at the front of the list.
550 /// Useful for updating contents.
551 ///
552 /// It basically does the same as `remove` and `push_back`, even if the specified index is already removed.
553 ///
554 /// # Panics
555 ///
556 /// Panics if index >= capacity
557 ///
558 /// # Examples
559 ///
560 /// ```
561 /// use array_linked_list::ArrayLinkedList;
562 ///
563 /// let mut array = ArrayLinkedList::new();
564 ///
565 /// array.push_front(1);
566 /// array.push_back(2);
567 /// let middle_index = array.push_back(3);
568 /// array.push_front(4);
569 /// array.push_back(5);
570 ///
571 /// let mut array2 = array.clone();
572 /// for (a, b) in array.iter().zip(&array2) {
573 /// assert_eq!(a, b)
574 /// }
575 ///
576 /// let element = array.replace_back(middle_index, 100);
577 /// let element2 = array2.remove(middle_index);
578 /// array2.push_back(100);
579 ///
580 /// assert_eq!(element, element2);
581 /// for (a, b) in array.iter().zip(&array2) {
582 /// assert_eq!(a, b)
583 /// }
584 ///
585 /// assert_eq!(array.len(), 5);
586 /// assert_eq!(array2.len(), 5);
587 /// ```
588 pub fn replace_back(&mut self, index: usize, value: T) -> Option<T> {
589 let LinkedListNode {
590 next_index,
591 prev_index,
592 data,
593 } = mem::replace(
594 &mut self.elements[index],
595 LinkedListNode::back(self.last_index, value),
596 );
597
598 let removed = data.is_some();
599 self.connect_indices(prev_index, next_index, removed);
600
601 if !removed {
602 self.count += 1;
603 }
604
605 if self.last_index > 0 {
606 self.elements[self.last_index - 1].next_index = index + 1;
607 }
608
609 self.last_index = index + 1;
610 data
611 }
612
613 /// Removes the first element from the array and returns it, or `None` if it is empty.
614 ///
615 /// This operation should compute in *O*(1) time.
616 ///
617 /// # Examples
618 ///
619 /// ```
620 /// use array_linked_list::ArrayLinkedList;
621 ///
622 /// let mut array = ArrayLinkedList::new();
623 /// assert_eq!(array.pop_front(), None);
624 /// array.push_back(1);
625 /// array.push_back(3);
626 /// assert_eq!(array.pop_front(), Some(1));
627 /// ```
628 pub fn pop_front(&mut self) -> Option<T> {
629 if self.first_index == 0 {
630 return None;
631 }
632 let index = self.first_index - 1;
633 let LinkedListNode {
634 next_index, data, ..
635 } = mem::replace(
636 &mut self.elements[index],
637 LinkedListNode::deleted(self.free_index),
638 );
639
640 *self.prev_of_next(next_index, true) = 0;
641 self.first_index = next_index;
642
643 self.count -= 1;
644 if self.free_index > 0 {
645 self.elements[self.free_index - 1].prev_index = index;
646 }
647
648 self.free_index = index;
649 Some(unsafe { data.unwrap_unchecked() })
650 }
651
652 /// Removes the last element from the array and returns it, or `None` if it is empty.
653 ///
654 /// This operation should compute in *O*(1) time.
655 ///
656 /// # Examples
657 ///
658 /// ```
659 /// use array_linked_list::ArrayLinkedList;
660 ///
661 /// let mut array = ArrayLinkedList::new();
662 /// assert_eq!(array.pop_back(), None);
663 /// array.push_back(1);
664 /// array.push_back(3);
665 /// assert_eq!(array.pop_back(), Some(3));
666 /// ```
667 pub fn pop_back(&mut self) -> Option<T> {
668 if self.last_index == 0 {
669 return None;
670 }
671 let index = self.last_index - 1;
672 let LinkedListNode {
673 prev_index, data, ..
674 } = mem::replace(
675 &mut self.elements[index],
676 LinkedListNode::deleted(self.free_index),
677 );
678
679 self.last_index = prev_index;
680 *self.next_of_prev(prev_index, true) = 0;
681
682 self.count -= 1;
683 if self.free_index > 0 {
684 self.elements[self.free_index - 1].prev_index = index;
685 }
686
687 self.free_index = index;
688 Some(unsafe { data.unwrap_unchecked() })
689 }
690
691 /// The index of the first list element.
692 /// Returns `None` if array is empty.
693 pub fn front_index(&self) -> Option<usize> {
694 if self.first_index > 0 {
695 Some(self.first_index - 1)
696 } else {
697 None
698 }
699 }
700
701 /// The index of the last list element.
702 /// Returns `None` if array is empty.
703 pub fn back_index(&self) -> Option<usize> {
704 if self.last_index > 0 {
705 Some(self.last_index - 1)
706 } else {
707 None
708 }
709 }
710
711 /// The first list element.
712 /// Returns `None` if array is empty.
713 pub fn front(&self) -> Option<&T> {
714 if self.first_index == 0 {
715 return None;
716 }
717
718 Some(unsafe {
719 self.elements[self.first_index - 1]
720 .data
721 .as_ref()
722 .unwrap_unchecked()
723 })
724 }
725
726 /// The last list element.
727 /// Returns `None` if array is empty.
728 pub fn back(&self) -> Option<&T> {
729 if self.last_index == 0 {
730 return None;
731 }
732
733 Some(unsafe {
734 self.elements[self.last_index - 1]
735 .data
736 .as_ref()
737 .unwrap_unchecked()
738 })
739 }
740
741 /// The first list element as a mutable reference.
742 /// Returns `None` if array is empty.
743 pub fn front_mut(&mut self) -> Option<&mut T> {
744 if self.first_index == 0 {
745 return None;
746 }
747
748 Some(unsafe {
749 self.elements[self.first_index - 1]
750 .data
751 .as_mut()
752 .unwrap_unchecked()
753 })
754 }
755
756 /// The last list element as a mutable reference.
757 /// Returns `None` if array is empty.
758 pub fn back_mut(&mut self) -> Option<&mut T> {
759 if self.last_index == 0 {
760 return None;
761 }
762
763 Some(unsafe {
764 self.elements[self.last_index - 1]
765 .data
766 .as_mut()
767 .unwrap_unchecked()
768 })
769 }
770
771 /// Checks if the list is empty.
772 pub fn is_empty(&self) -> bool {
773 self.first_index == 0 && self.last_index == 0
774 }
775
776 /// Clears the linked array, removing all values.
777 ///
778 /// Note that this method has no effect on the allocated capacity of the array.
779 /// So all indices, which have already been used (see `capacity`), are still available.
780 pub fn clear(&mut self) {
781 self.count = 0;
782 self.first_index = 0;
783 self.last_index = 0;
784 self.free_index = 0;
785 self.end_index = 0;
786
787 let capacity = self.elements.len();
788 self.elements.clear();
789 self.fill_elements(capacity);
790 }
791
792 /// Returns the number of elements in the linked array.
793 pub fn len(&self) -> usize {
794 self.count
795 }
796
797 /// Returns the number of elements the vector can hold without reallocating.
798 ///
799 /// Methods, which take indices, require the specified index to be below the capacity.
800 ///
801 /// All the following methods require indices:
802 ///
803 /// * `insert_before`
804 /// * `insert_after`
805 /// * `remove`
806 /// * `replace_front`
807 /// * `replace_back`
808 ///
809 /// Besides that, some of the iterators are constructed using indices in the same range.
810 pub fn capacity(&self) -> usize {
811 self.elements.len()
812 }
813
814 /// Returns a borrowing iterator over its elements.
815 pub fn iter(&self) -> impl DoubleEndedIterator<Item = &T> {
816 Values(Indexed::new(self))
817 }
818
819 /// Returns a borrowing iterator over its indexed elements.
820 pub fn indexed(&self) -> impl DoubleEndedIterator<Item = (usize, &T)> {
821 Indexed::new(self)
822 }
823
824 /// Returns a borrowing iterator over its indices.
825 pub fn indices(&self) -> impl DoubleEndedIterator<Item = usize> + '_ {
826 Indices(Indexed::new(self))
827 }
828
829 /// Returns a borrowing iterator over its elements, starting after the element at the specified index.
830 ///
831 /// # Panics
832 ///
833 /// Panics if index >= capacity
834 pub fn iter_after(&self, index: usize) -> impl DoubleEndedIterator<Item = &T> {
835 Values(Indexed::after(self, index))
836 }
837
838 /// Returns a borrowing iterator over its indexed elements, starting after the element at the specified index.
839 ///
840 /// # Panics
841 ///
842 /// Panics if index >= capacity
843 pub fn indexed_after(&self, index: usize) -> impl DoubleEndedIterator<Item = (usize, &T)> {
844 Indexed::after(self, index)
845 }
846
847 /// Returns a borrowing iterator over its indices, starting after the element at the specified index.
848 ///
849 /// # Panics
850 ///
851 /// Panics if index >= capacity
852 pub fn indices_after(&self, index: usize) -> impl DoubleEndedIterator<Item = usize> + '_ {
853 Indices(Indexed::after(self, index))
854 }
855
856 /// Returns a borrowing iterator over its elements, ending before the element at the specified index.
857 ///
858 /// # Panics
859 ///
860 /// Panics if index >= capacity
861 pub fn iter_before(&self, index: usize) -> impl DoubleEndedIterator<Item = &T> {
862 Values(Indexed::before(self, index))
863 }
864
865 /// Returns a borrowing iterator over its indexed elements, ending before the element at the specified index.
866 ///
867 /// # Panics
868 ///
869 /// Panics if index >= capacity
870 pub fn indexed_before(&self, index: usize) -> impl DoubleEndedIterator<Item = (usize, &T)> {
871 Indexed::before(self, index)
872 }
873
874 /// Returns a borrowing iterator over its indices, ending before the element at the specified index.
875 ///
876 /// # Panics
877 ///
878 /// Panics if index >= capacity
879 pub fn indices_before(&self, index: usize) -> impl DoubleEndedIterator<Item = usize> + '_ {
880 Indices(Indexed::before(self, index))
881 }
882
883 /// Returns an owning iterator returning its indexed elements.
884 pub fn into_indexed(self) -> impl DoubleEndedIterator<Item = (usize, T)> {
885 IntoIndexed(self)
886 }
887
888 /// Returns an owning iterator returning its indices.
889 pub fn into_indices(self) -> impl DoubleEndedIterator<Item = usize> {
890 IntoIndices(IntoIndexed(self))
891 }
892}
893
894impl<T> Index<usize> for ArrayLinkedList<T> {
895 type Output = Option<T>;
896 fn index(&self, index: usize) -> &Option<T> {
897 &self.elements[index].data
898 }
899}
900
901impl<T> IndexMut<usize> for ArrayLinkedList<T> {
902 fn index_mut(&mut self, index: usize) -> &mut Option<T> {
903 &mut self.elements[index].data
904 }
905}
906
907struct Indexed<'a, T> {
908 front_index: usize,
909 back_index: usize,
910 array: &'a ArrayLinkedList<T>,
911}
912
913impl<'a, T> Indexed<'a, T> {
914 fn empty(array: &'a ArrayLinkedList<T>) -> Self {
915 Self {
916 front_index: 0,
917 back_index: 0,
918 array,
919 }
920 }
921
922 fn new(array: &'a ArrayLinkedList<T>) -> Self {
923 Self {
924 front_index: array.first_index,
925 back_index: array.last_index,
926 array,
927 }
928 }
929
930 fn after(array: &'a ArrayLinkedList<T>, prev_index: usize) -> Self {
931 let element = &array.elements[prev_index];
932 if element.data.is_some() {
933 Self {
934 front_index: element.next_index,
935 back_index: array.last_index,
936 array,
937 }
938 } else {
939 Self::empty(array)
940 }
941 }
942
943 fn before(array: &'a ArrayLinkedList<T>, next_index: usize) -> Self {
944 let element = &array.elements[next_index];
945 if element.data.is_some() {
946 Self {
947 front_index: array.first_index,
948 back_index: element.prev_index,
949 array,
950 }
951 } else {
952 Self::empty(array)
953 }
954 }
955}
956
957struct Indices<'a, T>(Indexed<'a, T>);
958
959/// Borrowing iterator over values of the linked array.
960pub struct Values<'a, T>(Indexed<'a, T>);
961
962impl<'a, T> Iterator for Indexed<'a, T> {
963 type Item = (usize, &'a T);
964 #[inline]
965 fn next(&mut self) -> Option<Self::Item> {
966 if self.front_index == 0 {
967 return None;
968 }
969
970 let index = self.front_index - 1;
971 let element = &self.array.elements[index];
972 if self.front_index == self.back_index {
973 self.front_index = 0;
974 self.back_index = 0;
975 } else {
976 self.front_index = element.next_index;
977 }
978 Some((index, unsafe { element.data.as_ref().unwrap_unchecked() }))
979 }
980}
981
982impl<T> DoubleEndedIterator for Indexed<'_, T> {
983 #[inline]
984 fn next_back(&mut self) -> Option<Self::Item> {
985 if self.back_index == 0 {
986 return None;
987 }
988
989 let index = self.back_index - 1;
990 let element = &self.array.elements[index];
991 if self.front_index == self.back_index {
992 self.front_index = 0;
993 self.back_index = 0;
994 } else {
995 self.back_index = element.prev_index;
996 }
997 Some((index, unsafe { element.data.as_ref().unwrap_unchecked() }))
998 }
999}
1000
1001impl<T> Iterator for Indices<'_, T> {
1002 type Item = usize;
1003 fn next(&mut self) -> Option<Self::Item> {
1004 self.0.next().map(|(index, _)| index)
1005 }
1006}
1007
1008impl<T> DoubleEndedIterator for Indices<'_, T> {
1009 fn next_back(&mut self) -> Option<Self::Item> {
1010 self.0.next_back().map(|(index, _)| index)
1011 }
1012}
1013
1014impl<'a, T> Iterator for Values<'a, T> {
1015 type Item = &'a T;
1016 fn next(&mut self) -> Option<Self::Item> {
1017 self.0.next().map(|(_, value)| value)
1018 }
1019}
1020
1021impl<T> DoubleEndedIterator for Values<'_, T> {
1022 fn next_back(&mut self) -> Option<Self::Item> {
1023 self.0.next_back().map(|(_, value)| value)
1024 }
1025}
1026
1027impl<'a, T> IntoIterator for &'a ArrayLinkedList<T> {
1028 type Item = &'a T;
1029 type IntoIter = Values<'a, T>;
1030
1031 #[inline]
1032 fn into_iter(self) -> Self::IntoIter {
1033 Values(Indexed::new(self))
1034 }
1035}
1036
1037struct IntoIndexed<T>(ArrayLinkedList<T>);
1038struct IntoIndices<T>(IntoIndexed<T>);
1039
1040/// Owning iterator over values of the linked array.
1041pub struct IntoValues<T>(IntoIndexed<T>);
1042
1043impl<T> Iterator for IntoIndexed<T> {
1044 type Item = (usize, T);
1045 #[inline]
1046 fn next(&mut self) -> Option<Self::Item> {
1047 if self.0.first_index == 0 {
1048 return None;
1049 }
1050
1051 let index = self.0.first_index - 1;
1052 let element = &mut self.0.elements[index];
1053 if self.0.first_index == self.0.last_index {
1054 self.0.first_index = 0;
1055 self.0.last_index = 0;
1056 } else {
1057 self.0.first_index = element.next_index;
1058 }
1059 Some((index, unsafe { element.data.take().unwrap_unchecked() }))
1060 }
1061}
1062
1063impl<T> DoubleEndedIterator for IntoIndexed<T> {
1064 fn next_back(&mut self) -> Option<Self::Item> {
1065 if self.0.first_index == 0 {
1066 return None;
1067 }
1068
1069 let index = self.0.first_index - 1;
1070 let element = &mut self.0.elements[index];
1071 if self.0.first_index == self.0.last_index {
1072 self.0.first_index = 0;
1073 self.0.last_index = 0;
1074 } else {
1075 self.0.first_index = element.next_index;
1076 }
1077 Some((index, unsafe { element.data.take().unwrap_unchecked() }))
1078 }
1079}
1080
1081impl<T> Iterator for IntoIndices<T> {
1082 type Item = usize;
1083 fn next(&mut self) -> Option<Self::Item> {
1084 self.0.next().map(|(index, _)| index)
1085 }
1086}
1087
1088impl<T> DoubleEndedIterator for IntoIndices<T> {
1089 fn next_back(&mut self) -> Option<Self::Item> {
1090 self.0.next_back().map(|(index, _)| index)
1091 }
1092}
1093
1094impl<T> Iterator for IntoValues<T> {
1095 type Item = T;
1096 fn next(&mut self) -> Option<Self::Item> {
1097 self.0.next().map(|(_, value)| value)
1098 }
1099}
1100
1101impl<T> DoubleEndedIterator for IntoValues<T> {
1102 fn next_back(&mut self) -> Option<Self::Item> {
1103 self.0.next_back().map(|(_, value)| value)
1104 }
1105}
1106
1107impl<T> IntoIterator for ArrayLinkedList<T> {
1108 type Item = T;
1109 type IntoIter = IntoValues<T>;
1110
1111 fn into_iter(self) -> Self::IntoIter {
1112 IntoValues(IntoIndexed(self))
1113 }
1114}