算法训练营(day4)
Posted flyyyya
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了算法训练营(day4)相关的知识,希望对你有一定的参考价值。
核心考点:链表操作,思维缜密程度
解题思路:
定义三个指针,整体右移,边移动,边翻转,保证不会断链,这里我们要注意分别只有一个节点,两个节点和多个节点的情况。
class Solution {
public:
ListNode* ReverseList(ListNode* pHead) {
if (pHead == NULL || pHead->next == NULL)
{
return pHead;
}
ListNode* first = pHead;
ListNode* second = first->next;
ListNode* third = second->next;
while (third){
//翻转
second->next = first;
//指针整体后移
first = second;
second = third;
third = third->next;
}
second->next = first;//当传入的链表只有两个节点或者上述翻转结束最后一个并没有翻转
pHead->next = nullptr;
pHead = second;
return pHead;
}
};
核心考点:链表合并
解题思路:
在一个链表中插来插去比较混乱,这里我们定义一个新的链表,将数据往里插。
struct ListNode {
int val;
struct ListNode *next;
};
struct ListNode* merge(struct ListNode* l1, struct ListNode* l2)
{
struct ListNode* guard = (struct ListNode*)malloc(sizeof(struct ListNode));//申请一个头结点
struct ListNode* tail = guard;//尾指针
struct ListNode* cur1 = l1;//记录当前遍历到的l1链表的结点位置
struct ListNode* cur2 = l2;//记录当前遍历到的l2链表的结点位置
while (cur1&&cur2)//当l1,l2中有一个链表遍历完毕时便停止
{
//取小的结点尾插到新链表后面
if (cur1->val < cur2->val)
{
tail->next = cur1;
cur1 = cur1->next;
}
else
{
tail->next = cur2;
cur2 = cur2->next;
}
tail = tail->next;//结点增加,尾指针后移
}
//将未遍历完的链表的剩余结点接到新链表后面
if (cur1)
tail->next = cur1;
else
tail->next = cur2;
struct ListNode* head = guard->next;
free(guard);
return head;
}
核心考点:链表操作,临界条件检查,特殊情况处理
解题思路
通过快慢指针的方式,进而达到去重的结果这里要考虑特别多的特殊情况,如:全部相同,全部不相同,部分相同等,为了方便解题我们定义头结点,主要是应对全部。相同的情况。
class Solution {
public:
ListNode* deleteDuplication(ListNode* pHead) {
if (pHead == NULL)
{
return pHead;
}
ListNode* head = new ListNode(0);
head->next = pHead;
ListNode* prev = head;
ListNode* last = prev->next;
while (last!=NULL)
{
//1.确立重复区域的起始位置
while (last->next != NULL&&last->val != last->next->val)
{
prev = last;
last = last->next;
}
//2.确立重复区域
while (last->next != NULL&&last->val == last->next->val)
{
last = last->next;
}
if (prev->next != last)
{
prev->next = last->next;
}
last = last->next;
}
}
};
以上是关于算法训练营(day4)的主要内容,如果未能解决你的问题,请参考以下文章