92. Reverse Linked List II
题意:将链表中第m到第n个元素翻转
我的思路:指针数组
我的代码:
class Solution { public: ListNode* reverseBetween(ListNode* head, int m, int n) { vector<ListNode*> tmp(n-m+1); ListNode* ans = new ListNode(0), *l; ListNode* ret= ans; ans->next = head; int i = 0; while (ans) { if (i == m-1) { l = ans; ans = ans->next; for (int j = 0; j < n-m+1; j++) { tmp[j] = ans; ans = ans->next; } for (int j = n-m; j >= 0; j--) { l->next = tmp[j]; l = l->next; } l->next = ans; break; } ans = ans->next; i++; } return ret->next; } };
206. Reverse Linked List
题意:将链表转置
我的思路:递归实现,1A
我的代码:
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */ class Solution { public: ListNode* reverse(ListNode* head) { ListNode* ret = head; if (head->next) { ret = reverse(head->next); head->next->next = head; } return ret; } ListNode* reverseList(ListNode* head) { if (head == NULL) return head; ListNode* ans, *tmp = head; ans = reverse(head); tmp->next = NULL; return ans; } };
九章最优解:循环实现,被秒成了渣T T
class Solution { public: /** * @param head: The first node of linked list. * @return: The new head of reversed linked list. */ ListNode *reverse(ListNode *head) { ListNode *prev = NULL; while (head != NULL) { ListNode *temp = head->next; head->next = prev; prev = head; head = temp; } return prev; } };
128. Longest Consecutive Sequence
题意:给定一个数组,输出最长的连续数字长度,要求时间复杂度O(n)
我的思路:map记录都出现了什么数,然后搜每个数字上下共多少个数,查到的数都删除可以降低重复搜索
我的代码:
class Solution { public: int longestConsecutive(vector<int>& nums) { int ans = 0; map<int, int> m; for (int i = 0; i < nums.size(); i++) m[nums[i]] = 1; while (!m.empty()) { map<int, int>::iterator it = m.begin(); int tmp = 1, val = it->first, i = 1; m.erase(it); while (m.find(val+i) != m.end()) { m.erase(m.find(val+i)); i++; tmp++; } i = 1; while (m.find(val-i) != m.end()) { m.erase(m.find(val-i)); i++; tmp++; } ans = max(tmp, ans); } return ans; } };
133. Clone Graph
题意:复制一个无向图
我的思路:bfs加map
我的代码:
class Solution { public: UndirectedGraphNode *cloneGraph(UndirectedGraphNode *node) { if (node == NULL) return NULL; queue<UndirectedGraphNode *> q; map<UndirectedGraphNode *, UndirectedGraphNode *> m; map<UndirectedGraphNode *, bool> flag; q.push(node); flag[node] = 1; while (!q.empty()) { int n = q.size(); for (int i = 0; i < n; i++) { UndirectedGraphNode *tmp = q.front(); q.pop(); UndirectedGraphNode *hehe, *nei; if (m.find(tmp) == m.end()) { hehe = new UndirectedGraphNode(tmp->label); m[tmp] = hehe; } else hehe = m[tmp]; for (int j = 0; j < tmp->neighbors.size(); j++) { if (m.find(tmp->neighbors[j]) == m.end()) { nei = new UndirectedGraphNode(tmp->neighbors[j]->label); m[tmp->neighbors[j]] = nei; } else nei = m[tmp->neighbors[j]]; hehe->neighbors.push_back(nei); if (flag.find(tmp->neighbors[j]) == flag.end()) { q.push(tmp->neighbors[j]); flag[tmp->neighbors[j]] = 1; } } } } return m[node]; } };
138. Copy List with Random Pointer
题意:创建一个链表的深拷贝,其中含有随机指针
我的思路:走三遍,第一遍把每个节点复制出来坠在后边,第二遍给复制出的节点的随机指针复制,第三遍将复制出的节点提出来并将原链表复原
我的代码:
class Solution { public: RandomListNode *copyRandomList(RandomListNode *head) { RandomListNode *front = head; while (front) { RandomListNode *tmp= new RandomListNode(front->label); tmp->next = front->next; front->next = tmp; front = tmp->next; } front = head; while (front) { if (front->random) front->next->random = front->random->next; front = front->next->next; } RandomListNode *tmp = new RandomListNode(0); RandomListNode *ans = tmp; while (head) { tmp->next = head->next; tmp = tmp->next; head->next = head->next->next; head = head->next; } return ans->next; } };
141. Linked List Cycle
题意:判断链表中是否有环
我的思路:两个指针一快(每次两步)一慢(每次一步),如果不会相遇,则无环
我的代码:
class Solution { public: bool hasCycle(ListNode *head) { if (head == NULL) return 0; ListNode * fast = head, *slow = head; while (slow->next && fast->next && fast->next->next) { slow = slow->next; fast = fast->next->next; if (slow == fast) return 1; } return 0; } };
九章最优解:一样
class Solution { public: /** * @param head: The first node of linked list. * @return: True if it has a cycle, or false */ bool hasCycle(ListNode *head) { // write your code here ListNode *fast,*slow; if(head==NULL) return false; slow=head; fast=head->next; while(fast!=NULL && fast->next!=NULL) { if(slow==fast) return true; slow=slow->next; fast=fast->next->next; } return false; } };
142. Linked List Cycle II
题意:找到链表环的起点
我的思路:快慢指针,快的是慢的速度的两倍,两指针相遇时改为相同速度,则再次相遇时就是环的起点(画个图很容易理解)
我的代码:
class Solution { public: ListNode *detectCycle(ListNode *head) { if (head == NULL) return NULL; ListNode * fast = head, *slow = head; while (slow->next && fast->next && fast->next->next) { slow = slow->next; fast = fast->next->next; if (slow == fast) { slow = head; while (slow != fast) { slow = slow->next; fast = fast->next; } return slow; } } return NULL; } };
143. Reorder List
题意:将链表 L0→L1→…→Ln-1→Ln,重排为 L0→Ln→L1→Ln-1→L2→Ln-2→…
我的思路:指针数组。。
我的代码:
class Solution { public: void reorderList(ListNode* head) { vector<ListNode*> hehe; ListNode* tmp = head; while (tmp) { ListNode* gg = tmp; hehe.push_back(gg); tmp = tmp->next; } int n = hehe.size(), cnt = 0, i = 0; tmp = new ListNode(0); while (cnt < n) { tmp->next = hehe[i]; tmp = tmp->next; cnt++; if (cnt < n) { tmp->next = hehe[n-1-i]; tmp = tmp->next; cnt++; } i++; } tmp->next = NULL; } };
soluton解法:快慢指针,慢指针指到一半,将后半段倒置再合并
class Solution { public: void reorderList(ListNode* head) { if (head==nullptr || head->next==nullptr) return ; //Find mid of the link list ListNode *slow = head; ListNode *fast = head; while( fast && fast->next) { slow = slow->next; fast = fast->next->next; } //break link list and reverse the second ListNode* mid = slow->next; slow->next = nullptr; mid = reverseList(mid); //merge two link list mergeTwoLists(head, mid); } ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) { ListNode* head = new ListNode(0); ListNode* dummy = head; while(l1 && l2) { head->next = l1; head = head->next; l1=l1->next; head->next = l2; head = head->next; l2=l2->next; } head->next = l1 ? l1 : l2; return dummy->next; } ListNode* reverseList(ListNode* head) { ListNode* prev = NULL; while (head) { ListNode* next = head->next; head->next = prev; prev = head; head = next; } return prev; } };
147. Insertion Sort List
题意:链表的插入排序
我的思路:常规题,1A
我的代码:
class Solution { public: ListNode* insertionSortList(ListNode* head) { if (head == NULL) return NULL; ListNode* ans = new ListNode(0); while (head) { ListNode* tmp = ans; while (tmp->next && tmp->next->val < head->val) tmp = tmp->next; ListNode* hehe = new ListNode(head->val); hehe->next = tmp->next; tmp->next = hehe; head = head->next; } return ans->next; } };
148. Sort List
题意:链表归并排序
我的代码:
class Solution { public: ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) { ListNode *res = new ListNode(0); ListNode *ans = res; while (l1 && l2) { if (l1->val <= l2->val) { res->next = l1; l1 = l1->next; res = res->next; } else { res->next = l2; l2 = l2->next; res = res->next; } } if (l1) res->next = l1; else res->next = l2; return ans->next; } ListNode* sortList(ListNode* head) { if (head == NULL || head->next == NULL) return head; ListNode* f = head->next->next, *s = head; while (f && f->next) { f = f->next->next; s = s->next; } ListNode* r = sortList(s->next); s->next = NULL; return mergeTwoLists(sortList(head), r); } };
160. Intersection of Two Linked Lists
题意:两个链表会交汇成一条,求交汇的第一个结点,要求时间复杂度为O(n),空间复杂度为O(1)
我的思路:不会。。
solution解法:太妙!以麻花状遍历,两个指针分别从a、b走,a走完改道走b,另一个同理,他俩最多走两个链表长度必相遇(或者都是NULL)
class Solution { public: ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) { ListNode *cur1 = headA, *cur2 = headB; while(cur1 != cur2){ cur1 = cur1 ? cur1->next : headB; cur2 = cur2 ? cur2->next : headA; } return cur1; } };
九章最优解:
class Solution { public: /** * @param headA: the first list * @param headB: the second list * @return: a ListNode */ ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) { // write your code here if(headA == NULL || headB == NULL) return NULL; ListNode* iter1 = headA; ListNode* iter2 = headB; int len1 = 1; while(iter1->next != NULL) { iter1 = iter1->next; len1 ++; } int len2 = 1; while(iter2->next != NULL) { iter2 = iter2->next; len2 ++; } if(iter1 != iter2) return NULL; if(len1 > len2) { for(int i = 0; i < len1-len2; i ++) headA = headA->next; } else if(len2 > len1) { for(int i = 0; i < len2-len1; i ++) headB = headB->next; } while(headA != headB) { headA = headA->next; headB = headB->next; } return headA; } };
173. Binary Search Tree Iterator
题意:完成操作每次输出排序二叉树中下一个最小的值
我的思路:栈
我的代码:
class BSTIterator { public: TreeNode *gg; stack<TreeNode *> s; BSTIterator(TreeNode *root) { gg = root; } /** @return whether we have a next smallest number */ bool hasNext() { return !(gg == NULL && s.empty()); } /** @return the next smallest number */ int next() { TreeNode *ans; if (gg == NULL) { ans = s.top(); s.pop(); gg = ans->right; } else { while (gg->left) { s.push(gg); gg = gg->left; } ans = gg; gg = ans->right; } return ans->val; } };
203. Remove Linked List Elements
题意:去掉链表中的某个值
我的思路:常规题,写的不如人家好
我的代码:
class Solution { public: ListNode* removeElements(ListNode* head, int val) { ListNode *ans = head; while (head && head->val == val) { ans = head->next; head = head->next; } while (head && head->next) { if (head->next->val == val) head->next = head->next->next; else head = head->next; } return ans; } };
九章最优解:
class Solution { public: /** * @param head a ListNode * @param val an integer * @return a ListNode */ ListNode *removeElements(ListNode *head, int val) { ListNode dummy; dummy.next = head; head = &dummy; while (head->next != NULL) { if (head->next->val == val) { head->next = head->next->next; } else { head = head->next; } } return dummy.next; } };
234. Palindrome Linked List
题意:判链表是否回文,要求时间O(n)
我的思路:栈存放前半部分
我的代码:
class Solution { public: bool isPalindrome(ListNode* head) { if (head == NULL || head->next == NULL) return 1; stack<int> s; ListNode *fast = head, *slow = head; while (fast && fast->next) { s.push(slow->val); slow = slow->next; fast = fast->next->next; } if (fast) slow = slow->next; while (slow) { if (slow->val != s.top()) return 0; s.pop(); slow = slow->next; } return 1; } };
solution解法:递归,我服
class Solution { public: ListNode* temp; bool isPalindrome(ListNode* head) { temp=head; return check(head); } bool check(ListNode* p) { if(!p) return true; bool ispal=check(p->next)&&(temp->val==p->val); temp=temp->next; return ispal; } };
328. Odd Even Linked List
题意:将链表1、3、5……个节点放前边,2、4、6……个节点放后边形成一个新链表
我的思路:链表基本操作
我的代码:
class Solution { public: ListNode* oddEvenList(ListNode* head) { if (head == NULL) return head; ListNode *odd = new ListNode(0), *even = new ListNode(0); ListNode* ret = odd, *tmp = even; while (head && head->next) { odd->next = head; even->next = head->next; head = head->next->next; odd = odd->next; even = even->next; } if (head) { odd->next = head; odd = odd->next; } even->next = NULL; odd->next = tmp->next; return ret->next; } };
382. Linked List Random Node
题意:等概率输出链表的节点值
我的思路:蓄水池采样
我的代码:
class Solution { public: ListNode* h; /** @param head The linked list's head. Note that the head is guaranteed to be not null, so it contains at least one node. */ Solution(ListNode* head) { h = head; } /** Returns a random node's value. */ int getRandom() { int n = 1, ans; ListNode* tmp = h; while (tmp) { if (rand()%n == 0) ans = tmp->val; n++; tmp = tmp->next; } return ans; } };