1. 寻找链表中间结点
ps.此题出于LeetCode网。
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* middleNode(struct ListNode* head){
int* n = (int*)malloc(sizeof(int) * 100);
struct ListNode* cur = head;
int i = 0;
while (cur)
{
n[i] = cur->val;
cur = cur->next;
i++;
}
int tmp = 0;
if ((i + 1) % 2 == 0)
tmp = (i + 1) / 2 - 1;
else
tmp = (i + 1) / 2 ;
cur = head;
i = 0;
while (i != tmp)
{
cur = cur->next;
i++;
}
return cur;
}
//此处给出代码不再详细分析
struct ListNode* middleNode(struct ListNode* head){
struct ListNode* fast = head;
struct ListNode* slow = head;
while(fast && fast->next) //注意!!!
{
fast = fast->next->next;
slow = slow->next;
}
return slow;
}
//一定要注意while条件的写法,一定是fast在前,fast->next
//在后的因为while判断括号中的条件时是从左向右执行的,如果
//fast为NULL,那么fast->next这种写法是非法的!!
2.链表中倒数第k个结点
这道题如果用常规的方法就是先遍历计算出n个结点,然后从头找到正数的第(n-k)个结点,再返回第n-k个结点,是比较麻烦的。但如果用双指针的方法会简单许多。
分析:创建fast和slow两个指针都指向第一个结点,先让fast走k步,然后fast和slow一起走。这样一来fast和slow之间永远相差k步,当fast走到最后时,slow正好走到倒数第K个结点。返回slow。
struct ListNode* FindKthToTail(struct ListNode* pListHead, int k ) {
struct ListNode* fast = pListHead;
struct ListNode* slow = pListHead;
if (pListHead != NULL)
{
while(k--)
{
if(fast == NULL)//k>n k<0的情况
return NULL;
fast = fast->next;
}
while(fast)
{
fast = fast->next;
slow = slow->next;
}
return slow;
}
else
return NULL;
}