起因是正在做力扣的链表题目,做到第203题的时候,想到的是用迭代的方法求解的,如下:
class Solution {
public:
ListNode* removeElements(ListNode* head, int val) {
//创建一个虚拟头节点,就可以省略掉判断原始头节点的步骤了
ListNode *first=new ListNode(-1);
first->next=head;
ListNode *cur=first;
while(cur!=NULL&&cur->next!=NULL){
if(cur->next->val==val){
ListNode *tmp=cur->next;
cur->next=cur->next->next;
delete tmp; //记得删除内存占用
}
else cur=cur->next;
}
head=first->next;
delete first;
return head;
}
};
之后看了官方的解题思路里,有递归的方法做的,短短几行代码:
class Solution {
public:
ListNode* removeElements(ListNode* head, int val) {
if(head==NULL){
return head;
}
head->next=removeElements(head->next,val);
return head->val==val?head->next:head;
}
};
我都惊呆了,因为一直以来都不会用递归来作题,一直都理解不了怎么个递归法。
第一次接触递归,是在补《数据结构》课程的时候,有个很常见的求数组和的问题,用线性递归求解复杂度是0(n),而迭代的复杂度是0(n²),于是也只是简单的把代码记下来遇到问题用就行,直到又碰到了这个问题,给我整不会了。
下面可以分享一下我对递归详细的理解方法,比较笨拙但是能让自己看懂就好:
以203题官方递归解题代码为例,假定给的链表数是 [1,2,6,3,4,5,6]
如果从头往后分析,会发现每一次的head->next 都与后一项有关,不妨从尾往前一个一个来看
假设一共n项:
需要先明确两点:① 每一次递归部分都是会把这一次的head->next作为下一次的head
② 每一次的head->next都是下一次执行removeElements函数的返回值
这一题要求返回的只是指针,并不是把指针的数输出来了。
-第n项: head == NULL
head->val
head->next->valreturn开始 1→↙2→1 结束2→↙3→↖26→↙3→↖33→↙4→↖34→↙5→↖45→↙ NULL→↖56→↙NULL→↖NULLNULL→无了→↖NULL箭头就是我大概理解的递归的一步一步的方向,很粗糙,但我总算捋清楚了!!!!