Algo~

熟读并背诵全文。


1. 并查集

int find(int x) { 
    return pre[x] == x ? x : pre[x] = find(pre[x]); 
}
void merge(int a, int b){
    pre[find(a)] = find(b);
}

2. 快排

稳定性:不稳定
时间复杂度:O(n2)/O(nlgn),空间复杂度:O(1)

int partition(int* vec, int start, int end){
    int pos = start;
    for(int i = start; i < end; ++i){
        if(vec[i] < vec[end]) swap(vec[i], vec[pos++]);
    }
    swap(vec[pos], vec[end]);
    return pos;
}
void quick_sort(int* vec, int start, int end){
    if(start >= end) return;
    int pos = partition(vec, start, end);
    quick_sort(vec, start, pos - 1);
    quick_sort(vec, pos + 1, end);
}

3. 插入排序

稳定性:稳定
时间复杂度:O(n2),空间复杂度:O(1)

void insert_sort(int* vec, int start, int end){
    if(start >= end) return;
    int n = end - start + 1;
    for(int pos = 0; pos < n; ++pos){
        int curr = vec[pos];
        int i = pos - 1;
        for(; i >= 0 && vec[i] > curr; --i){
            vec[i + 1] = vec[i];
        }
        vec[i + 1] = curr;
    }
}

4. 选择排序

稳定性:不稳定
时间复杂度:O(n2),空间复杂度:O(1)

void select_sort(int* vec, int start, int end){
    if(start >= end) return;
    for(int i = start; i < end; ++i){
        swap(vec[i], *min_element(vec + i, vec + end + 1));
    }
}

5. 二分查找

时间复杂度:O(lgn),空间复杂度:O(1)

int binary_search(int* vec, int start, int end, int target){
    int lo = start, hi = end;
    while(lo <= hi){
        int mid = lo + ((hi - lo) >> 1);
        if(vec[mid] < target) lo = mid + 1;
        else if(vec[mid] == target) return mid;
        else hi = mid - 1;
    }
    return -1;
}
int lower_bound(int* vec, int start, int end, int target){
    int lo = start, hi = end;
    while(lo < hi){
        int mid = lo + ((hi - lo) >> 1);
        if(vec[mid] < target) lo = mid + 1;
        else hi = mid;
    }
    return hi;
}
int upper_bound(int* vec, int start, int end, int target){
    int lo = start, hi = end;
    while(lo < hi){
        int mid = (lo + hi + 1) >> 1;
        if(vec[mid] <= target) lo = mid;
        else hi = mid - 1;
    }
    return lo;
}

6. 层序遍历二叉树(BFS)

queue<TreeNode*> Q;
if(root) Q.push(root);
while(!Q.empty()){
    for(int i = Q.size(); i > 0; --i){
        TreeNode* curr = Q.front(); Q.pop();
        ... // 处理当前节点
        if(curr->left) Q.push(curr->left);
        if(curr->right) Q.push(curr->right);
    }
}

7. 链表反转

迭代三指针法

Node* list_reverse(Node* head){
    if(head == nullptr || head->next == nullptr) return head;
    Node* prev = nullptr, *curr = head, *next = head->next;
    while(curr){
        curr->next = prev;
        prev = curr;
        curr = next;
        if(next) next = next->next;
    }
    return prev;
}

8. 有序链表合并

递归法

Node* list_merge(Node* l1, Node* l2){
    if(l1 == nullptr) return l2;
    if(l2 == nullptr) return l1;
    if(l1->val <= l2->val){
        l1->next = list_merge(l1->next, l2);
        return l1;
    }else{
        l2->next = list_merge(l1, l2->next);
        return l2;
    }
    return l1;
}

你可能感兴趣的:(C++,算法)