数据结构——判断一个链表是否为回文结构,时间复杂度O(N)空间复杂度为O(1)
程序员文章站
2022-06-03 13:41:13
...
作者:小 琛
欢迎转载,请标明出处
题目:
思路一:
该题目的最后一句话目的为降低难度,我们完全可以就这句话定义一个大小为900的数组,然后遍历该链表两次,第一次记录链表的每一个值并存入数组,并以一个变量count记录总数。第二次遍历的时候我们进行比对,数组倒着走,链表正常走,全部相等则为互文
注意事项:
1、因为我们遍历链表的条件是一个指针是否为空,所以记录数量的count的值在第一次遍历后要减一,count-1才是正确的数组下标
2、第二次遍历链表进行比对的时候让每比对一次count–
代码如下:
int ChkPalindrome1(PlistNode* head)
{
PlistNode* n1 = head;
PlistNode* n2 = head;
int arr[900];
int count = 0;
while (n2 != NULL)
{
arr[count++] = n2->_date;
n2 = n2->_next;
}
count--;
n2 = NULL;
while (n1 != NULL)
{
if (n1->_date != arr[count--])
return 0;
n1 = n1->_next;
}
return 1;
}
思路二:
当面试官要求不允许开辟数组进行存储的时候,我们思路一就行不通了,思路二有一定的难度,共进行如下操作
1、先寻找该链表的中点处,并记录
2、使用操作1记录的指针,逆置后一半的链表,并得到逆置后的新头,看下图
3、就n1和n2两个头开始遍历比较,以两者不为空为判断条件,全部相同则为互文,如果有一个不相同,则直接返回0
需要用到两个知识:寻找链表的中点,逆置一个链表。这两个知识点在上篇博文《数据结构——快慢指针》有讲述,需要的请回看,这里直接上代码
int ChkPalindrome(PlistNode* head)
{
PlistNode* n1 = head;
PlistNode* n2 = head;
while (n2->_next != NULL && n2 != NULL)
{
n1 = n1->_next;
n2 = n2->_next;
n2 = n2->_next;
}
n2 = head;
//寻找中点
PlistNode* a1 = n1;
PlistNode* a2 = a1->_next;
PlistNode* a3 = a2->_next;
a1->_next = NULL;
while (a2 != NULL)
{
a2->_next = a1;
a1 = a2;
a2 = a3;
if (a3 != NULL)
a3 = a3->_next;
}
//逆置后一半
n1 = a1;
a1 = a2 = a3 = NULL;
while (n1 != NULL&&n2 != NULL) //进行比对
{
if (n1->_date != n2->_date)
return 0;
n1 = n1->_next;
n2 = n2->_next;
}
return 1;
}
感谢浏览
下一篇: clob保存为本地xml文件,修改后上传