😁题目
![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/5c487683637c4eec84fc5f5a4ca2ab2f.png# 😊解法
😉1.数组
定义一个数组,依次存储链表中的值,然后比较数组前和后的值,依次向内比较
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
bool isPalindrome(struct ListNode* head) {
int vals[100001],num = 0;
while(head)
{
vals[num++] = head->val;
head = head->next;
}
for(int i = 0,j=num -1; i < j; i++, j--)
{
if(vals[i] != vals[j])
return false;
}
return true;
}
😵💫2.递归
有点难以理解,递归的最后传入的是NULL,下一次递归调用的是最后一个结点,然后借助全局变量front(先保存头结点),front不断遍历结点和递归每一次调用的结点比较,不同则不是回文链表。
1 | 2 | ··· | -2 | -1 | 最后一次递归返回 |
---|---|---|---|---|---|
head | head->next | ···· | 倒数第二个结点 | 最后一个结点 | NULL |
struct ListNode* front;
bool re(struct ListNode* cur)
{
/*
因为最后递归的是NULL,所以返回true,跳过第一个if,
进入最后一个结点和头结点的比较,如果两个结点的值相等,则返回true,
依旧跳过第一个if,进行比较值的大小,然后递归和front不断向中间靠近,直到有不相等的
值出现,函数返回false,该链表不是回文链表
*/
if(cur!=NULL)
{
if(!re(cur->next))
return false;
if(cur->val != front->val)
return false;
front = front->next;
}
return true;
}
bool isPalindrome(struct ListNode* head) {
front = head;
return re(front);
}
😍3.快慢指针
本解法依赖知识:反转链表,快慢指针
struct ListNode* reverse(struct ListNode* head)
{
if(!head || !head->next)
return head;
struct ListNode *pre = NULL, *next = NULL, *cur = head;
while(cur)
{
next = cur->next;
cur->next = pre;
pre = cur;
cur = next;
}
return pre;
}
struct ListNode* SlowAndFast(struct ListNode* head)
{
struct ListNode *slow = head;
struct ListNode *fast = head;
while(fast->next && fast->next->next)
{
slow = slow->next;
fast = fast->next->next;
}
return slow;
}
bool isPalindrome(struct ListNode* head) {
if(!head || !head->next)
return head;
struct ListNode *FirstList = SlowAndFast(head);
struct ListNode *SecondList = reverse(FirstList->next);
struct ListNode *p1 = head, *p2 = SecondList;
bool result = true;
while(result && p2 != NULL)
{
if(p1->val != p2->val)
result = false;
p1 = p1->next;
p2 = p2->next;
}
FirstList->next = reverse(SecondList); //将修改后的head,修改回去
return result;
}