从尾到头打印链表
思路:最简单的一种想法就是遍历链表,用栈来保存数据,然后从栈中取出,代码比较简单:
public ArrayList<Integer> printListFromTailToHead(ListNode listNode) {
Stack<Integer> stack = new Stack<>();
while (listNode != null) {
stack.add(listNode.val);
listNode = listNode.next;
}
ArrayList<Integer> ret = new ArrayList<>();
while (!stack.isEmpty())
ret.add(stack.pop());
return ret;
}
我们还可以使用回溯法,回忆回溯法的特点,就是只有走到递归的出口才会有返回值,也就是遍历到链表最后一个节点才会有返回值,那么刚好符合我们题目从尾部输出的要求:
public ArrayList<Integer> ret = new ArrayList<>();
public ArrayList<Integer> printListFromTailToHead(ListNode listNode) {
helper(listNode);
return ret;
}
public void helper(ListNode listNode){
if(listNode == null) return;
if(listNode.next == null){//此判断可以去掉
ret.add(listNode.val);
return;
}
helper(listNode.next);
ret.add(listNode.val);
}
这个代码也可以简化一下,要逆序打印链表 1->2->3(3,2,1),可以先逆序打印链表 2->3(3,2),最后再打印第一个节点 1。而链表 2->3 可以看成一个新的链表,要逆序打印该链表可以继续使用求解函数,也就是在求解函数中调用自己,利用的也是回溯的特性,但是这个没有上面那个好理解:
public ArrayList<Integer> printListFromTailToHead(ListNode listNode) {
ArrayList<Integer> ret = new ArrayList<>();
if (listNode != null) {
ret.addAll(printListFromTailToHead(listNode.next));
ret.add(listNode.val);
}
return ret;
}
最后,还有一种方法,我们可以创建一个虚拟的头指针,然后将整个链表从头到尾往这个虚拟指针后面插,插完后,虚拟指针后面的节点就是整个链表的逆序啦,点这里可以看动图便于理解哦(●ˇ∀ˇ●)
public ArrayList<Integer> printListFromTailToHead(ListNode listNode) {
// 头插法构建逆序链表
ArrayList<Integer> ret = new ArrayList<>();
if(listNode == null) return ret;
ListNode dummy = new ListNode(-1);
dummy.next = listNode;
while (listNode.next != null) {
ListNode next = listNode.next;
listNode.next = next.next;
next.next = dummy.next;
dummy.next = next;
}
dummy = dummy.next;
while (dummy != null) {
ret.add(dummy.val);
dummy = dummy.next;
}
return ret;
}
//这种也可
public ArrayList<Integer> printListFromTailToHead(ListNode listNode) {
// 头插法构建逆序链表
ListNode dummy = new ListNode(-1);
while (listNode != null) {
ListNode memo = listNode.next;
listNode.next = dummy.next;
dummy.next = listNode;
listNode = memo;
}
// 构建 ArrayList
ArrayList<Integer> ret = new ArrayList<>();
dummy = dummy.next;
while (dummy != null) {
ret.add(dummy.val);
dummy = dummy.next;
}
return ret;
}