Leetcode碰巧又出现这个问题,看来面试算法这个是很常见的题型,不过很久没写过,这次写来又花了不少时间,
主要耽搁在思想的选择上:
一是想通过遍历时直接将指针反转,这样比较高效,但是需要处理好前后指针及后续的关系;
/** * Definition for singly-linked list. * struct ListNode { * int val; * struct ListNode *next; * }; */ struct ListNode* reverseList(struct ListNode* head) { struct ListNode *pre = NULL; struct ListNode *p = head; while(p) { struct ListNode *tmpNext = p->next;//current next node p->next = pre; pre = p; p = tmpNext; } return pre; }
二是通过构建一个新的链表头,然后遍历时直接将链表元素加入到新链接中,该算法比较简明;
/** * Definition for singly-linked list. * struct ListNode { * int val; * struct ListNode *next; * }; */ struct ListNode* reverseList(struct ListNode* head) { struct ListNode newListHead = { 0, NULL }; struct ListNode *p = head;//first node while(p) { struct ListNode *tmpnew = newListHead.next; struct ListNode *tmp = p->next; newListHead.next = p; p->next = tmpnew; p = tmp; } return newListHead.next; }
三是使用递归遍历链表至倒数第二位元素,接着依次将next指针反转:
/** * Definition for singly-linked list. * struct ListNode { * int val; * struct ListNode *next; * }; */ struct ListNode* reverseList(struct ListNode* head) { if (head == NULL || head->next == NULL){ return head; } struct ListNode* p = reverseList(head->next); head->next->next = head; head->next = NULL; return p; }这种方法还是从leetcode中才看到,类似于栈的操作,有一定启发性。