LeetCode算法题解:滑动窗口与链表操作
水果装入篮子问题
题目链接:水果装入篮子
这道题可以使用滑动窗口的思路来解决。我们需要维护一个窗口,其中最多包含两种类型的水果。使用双指针技术,一个指针(left)标记窗口的左边界,另一个指针(right)用于遍历数组。
具体思路:
- 使用哈希表记录当前窗口中的水果种类及其数量
- 移动右指针,将新水果加入窗口
- 当窗口中水果种类超过两种时,移动左指针缩小窗口
- 记录窗口的最大长度
参考代码:
class Solution {
public:
int totalFruit(vector<int>& fruits) {
unordered_map basket; // 记录水果种类和数量
int left = 0, max_len = 0;
for (int right = 0; right < fruits.size(); right++) {
basket[fruits[right]]++; // 将当前水果加入篮子
// 当篮子中水果种类超过两种时
while (basket.size() > 2) {
basket[fruits[left]]--; // 从左边移除水果
if (basket[fruits[left]] == 0) {
basket.erase(fruits[left]); // 如果数量为0,移除该种类
}
left++; // 左指针右移
}
// 更新最大窗口长度
max_len = max(max_len, right - left + 1);
}
return max_len;
}
};
移除链表元素
题目链接:移除链表元素
这道题要求删除链表中所有等于特定值的节点。为了处理头节点被删除的情况,我们可以使用虚拟头节点(dummy head)。
具体思路:
- 创建一个虚拟头节点,其next指向链表头
- 使用两个指针:prev指向当前节点的前一个节点,curr指向当前节点
- 遍历链表,如果curr的值等于目标值,则跳过curr节点
- 否则,prev和curr都向后移动
参考代码:
class Solution {
public:
ListNode* removeElements(ListNode* head, int val) {
// 创建虚拟头节点
ListNode* dummy = new ListNode(0);
dummy->next = head;
ListNode* prev = dummy;
ListNode* curr = head;
while (curr != nullptr) {
if (curr->val == val) {
// 跳过当前节点
prev->next = curr->next;
ListNode* temp = curr;
curr = curr->next;
delete temp; // 释放内存
} else {
// 移动两个指针
prev = curr;
curr = curr->next;
}
}
ListNode* newHead = dummy->next;
delete dummy; // 释放虚拟头节点
return newHead;
}
};
删除链表的倒数第N个节点
题目链接:删除链表的倒数第N个节点
这道题可以使用快慢指针的方法来解决。让快指针先走n步,然后快慢指针同时移动,当快指针到达链表末尾时,慢指针指向倒数第n个节点的前一个节点。
具体思路:
- 创建虚拟头节点,处理头节点被删除的情况
- 初始化快慢指针都指向虚拟头节点
- 让快指针先移动n+1步
- 然后快慢指针同时移动,直到快指针指向末尾
- 此时慢指针的下一个节点就是需要删除的节点
参考代码:
class Solution {
public:
ListNode* removeNthFromEnd(ListNode* head, int n) {
ListNode* dummy = new ListNode(0);
dummy->next = head;
ListNode* fast = dummy;
ListNode* slow = dummy;
// 快指针先移动n+1步
for (int i = 0; i <= n; i++) {
fast = fast->next;
}
// 快慢指针同时移动,直到快指针到达末尾
while (fast != nullptr) {
fast = fast->next;
slow = slow->next;
}
// 删除倒数第n个节点
ListNode* toDelete = slow->next;
slow->next = toDelete->next;
delete toDelete;
ListNode* newHead = dummy->next;
delete dummy;
return newHead;
}
};