LeetCode 21-29题解

21 简单

Solution

  • 模拟

Sample Code

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
public:
    ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
        ListNode * l = l1;
        ListNode * r = l2;
        if(!l && !r) return nullptr;
        if(!l) return r;
        if(!r) return l;
        ListNode * res = nullptr, * p;
        while(l && r){
            if(l->val <= r->val){
                if(res == nullptr) p = res = l;
                else {
                    p->next = l;
                    p = p->next;
                }
                l = l->next;
            }else{
                if(res == nullptr) p = res = r;
                else {
                    p->next = r;
                    p = p->next;
                }
                r = r->next;
            }
        }
        p->next = l ? l : r;

        return res;
    }
};

22 中等

Solution

  • dfs
  • 前缀中'('的数量不少于')'即可

Sample Code

class Solution {
public:
    vector<string> generateParenthesis(int n) {
        vector<string> vecRes; string res = "";
        dfs(vecRes, res, n, n);
        return vecRes;
    }
    void dfs(vector<string> & vecRes, string tmp, int l, int r){
        if(l == 0 && r == 0){
            vecRes.push_back(tmp);
            return;
        }
        if(l){
            tmp += '(';
            dfs(vecRes, tmp, l - 1, r);
            tmp = tmp.substr(0, tmp.length() - 1);
        }
        if(r && r > l){
            tmp += ')';
            dfs(vecRes, tmp, l, r - 1);
            tmp = tmp.substr(0, tmp.length() - 1);
        }
    }
};

23 困难

Solution

  • 归并

Sample Code

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* mergeKLists(vector<ListNode*>& lists) {
        int len = lists.size();
        return len ? mergeSort(lists, 0, len - 1) : nullptr;
    }
    ListNode * mergeSort(vector<ListNode*>& lists, int l, int r){
        if(l == r) return lists[l];
        int mid = (l + r) >> 1;
        ListNode * llist = mergeSort(lists, l, mid);
        ListNode * rlist = mergeSort(lists, mid + 1, r);
        return mergeList(llist, rlist);
    }
    ListNode * mergeList(ListNode * l, ListNode * r){
        if(!l && !r) return nullptr;
        if(!l) return r;
        if(!r) return l;
        ListNode * res = nullptr, * p;
        while(l && r){
            if(l->val <= r->val){
                if(res == nullptr) p = res = l;
                else {
                    p->next = l;
                    p = p->next;
                }
                l = l->next;
            }else{
                if(res == nullptr) p = res = r;
                else {
                    p->next = r;
                    p = p->next;
                }
                r = r->next;
            }
        }
        p->next = l ? l : r;
        return res;
    }
};

24 中等

Solution

  • 链表操作
  • 模拟

Sample Code

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
public:
    ListNode* swapPairs(ListNode* head) {
        ListNode * vHead = new ListNode(-1, head);
        ListNode * cur = vHead;
        while(cur->next && cur->next->next){
            ListNode * p = cur->next;
            ListNode * q = p->next;
            p->next = q->next;
            cur->next = q;
            q->next = p;
            cur = p;
        }
        return vHead->next;
    }
};

25 困难

Solution

  • 分组翻转即可
  • 先保存翻转后的尾部,翻转后接上后续结点
  • 用递推查找分组

Sample Code

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode() : val(0), next(nullptr) {}
 *     ListNode(int x) : val(x), next(nullptr) {}
 *     ListNode(int x, ListNode *next) : val(x), next(next) {}
 * };
 */
class Solution {
public:
    ListNode* reverseKGroup(ListNode* head, int k) {
        if(k == 1) return head;
        ListNode * vHead = new ListNode(-1, head);
        ListNode * cur = vHead; ListNode * tail;
        while(tail = pre(cur, k)){
            ListNode * tmpHead = cur->next; ListNode *tmpTailNext = tail->next;
            tail->next = nullptr;
            ListNode * newHead = reverse(tmpHead, tail);
            tmpHead->next = tmpTailNext;
            cur->next = newHead;
            cur = tmpHead;
        }
        return vHead->next;
    }
    ListNode * pre(ListNode * head, int step){
        while(head && step){
            head = head->next;
            step--;
        }
        return head;
    }
    ListNode * reverse(ListNode * head, ListNode * tail){
        ListNode * cur = head; ListNode * pre = nullptr;
        while(cur){
            ListNode * tmp = cur->next;
            cur->next = pre;
            pre = cur;
            cur = tmp;
        }
        return pre;
    }
};

26 简单

Solution

  • 和前一个元素对比,判断是否加入到新数组中

Sample Code

class Solution {
public:
    int removeDuplicates(vector<int>& nums) {
        if(nums.size() == 0) return 0;
        int cnt = 0;
        for(int i = 1; i < nums.size(); ++i){
            if(nums[i] != nums[i - 1]) 
                nums[++cnt] = nums[i];
        }
        return cnt + 1;
    }
};

27 简单

Solution

  • 26简单变种

Sample Code

class Solution {
public:
    int removeElement(vector<int>& nums, int val) {
        if(nums.size() == 0) return 0;
        int cnt = -1;
        for(int i = 0; i < nums.size(); ++i){
            if(nums[i] != val) 
                nums[++cnt] = nums[i];
        }
        return cnt + 1;
    }
};

28 简单

Solution

  • 模拟(O(len_1*len_2))
  • KMP

Sample Code(kmp)

class Solution {
public:
    int Next[100010];
    void getNext(string s){
        Next[0] = -1; Next[1] = 0;
        int i = 1; int j = 0;
        while(s[i]){
            while(~j && s[i] != s[j]) j = Next[j];
            ++i; ++j;
            Next[i] = s[i] != s[j] ? j : Next[j];
        }
    }
    int kmp(string s, string f){
        int i = 0; int j = 0;int len = f.length();
        while(s[i]){
            while(~j && s[i] != f[j]) j = Next[j];
            ++i; ++j;
            if(j == len) return i - len;
        }
        return -1;
    }
    int strStr(string haystack, string needle) {
        if(needle == "") return 0;
        getNext(needle);
        return kmp(haystack, needle);
    }
};

29 中等

Solution

  • 二分 + 乘法分解成加法
  • 乘法分解可参考快速幂,原理相似
  • 特判符号

Sample Code

class Solution {
public:
    long long abs(long long x){
        return x > 0 ? x : -x;
    }
    int divide(int dividend, int divisor) {
        long long a = dividend; 
        long long b = divisor;
        long long A = abs(a);
        long long B = abs(b);
        int c = 1; 
        if(a > 0 && b < 0) c = -1;
        if(a < 0 && b > 0) c = -1;
        long long ans = div(A, B);
        int up = (1 << 30) - 1 + (1 << 30);
        return c * ans > up ? up : c * ans;
    }
    long long div(long long a, long long b){
        long long l = 0; long long r = a;
        while(l <= r){
            long long m = (l + r) >> 1;
            long long mod = a - multiply(m, b);
            if(mod < b && mod >= 0) return m;
            if(mod < 0) r = m - 1;
            else l = m + 1;
        }
        return -1;
    }
    long long multiply(long long a, long long b){
        long long res = 0;
        while(a){
            if(a & 1) res += b;
            a = a >> 1;
            b = b + b;
        }
        return res;
    }
};
不忘初心
原文地址:https://www.cnblogs.com/CodingDreamer/p/15305112.html