Одним из решений, которое уже было предложено, является решение XOR .
Другим решением является решение "перевернутые стороны":
Если ваша проблема сформулирована следующим образом:
Вам дан указатель на первый элемент, и вы хотели бы:
- Перейти в связанном списке i шаги в O (i)
- Вернитесь в связанный список i, войдите в O (i)
- Добавить или удалить элементы в текущем местоположении в O (1)
Так что всегда есть только один указатель на связанный список, и есть только одна точка входа (просто переход вперед и назад, как в 1 и 2), вы можете сделать следующее:
- Сохранить два указателя: p1 , p2
- От первого указателя p1 вы можете вернуться назад, от второго указателя p2 вы идете вперед.
- Элементы связанного списка, предшествующие p1 , указывают назад, а элементы после p2 указывают вперед.
Итак, ваш список будет выглядеть так:
p1 p2
| |
V V
i1 <- i2 <- i3 <- i4 i5 -> i6 -> i7
p1 указывает на текущий элемент, p2 указывает на следующий элемент, i1 ... i7 - элементы в списке
Движение вперед выполняется в O (1), и то же самое происходит назад, переключая указатели:
Forward one step:
p1 p2
| |
V V
i1 <- i2 <- i3 <- i4 <- i5 i6 -> i7
Backward one step:
p1 p2
| |
V V
i1 <- i2 <- i3 i4 -> i5 -> i6 -> i7
Это решение лучше, чем решение XOR, по своей читабельности и тому, что оно более понятно для человека. Недостатком является то, что вы не можете иметь несколько точек входа в свой связанный список.