1. 程式人生 > 實用技巧 >LeetCode第205場周賽

LeetCode第205場周賽

1. 替換所有的問號

遍歷替換,時間複雜度\(O(n)\)

class Solution {
public:
    string modifyString(string s) {
        for(int i = 0; i < s.size(); i++) {
            if(s[i] == '?') {
                for(int j = 0; j < 26; j++) {
                    if((!i || (s[i - 1] - 'a') != j) && (i == s.size() - 1 || (s[i + 1] - 'a') != j)) s[i] = 'a' + j;
                }
            }
        }
        return s;
    }
};

2. 數的平方等於兩數乘積的方法數

需要求兩個相似的解,可以把重複的程式碼封裝成函式,時間複雜度\(O(n^2)\)

class Solution {
public:
    int cal(vector<int>& nums1, vector<int>& nums2) {
        int n1 = nums1.size(), n2 = nums2.size(), cnt = 0;
        unordered_map<long long, int> m;
        for(int i = 0; i < n1; i++) m[1LL * nums1[i] * nums1[i]]++;
        for(int i = 0; i < n2; i++) {
            for(int j = i + 1; j < n2; j++) cnt += m[1LL * nums2[i] * nums2[j]];
        }
        return cnt;
    }

    int numTriplets(vector<int>& nums1, vector<int>& nums2) {
        return cal(nums1, nums2) + cal(nums2, nums1);
    }
};

3. 避免重複字母的最小刪除成本

貪心,時間複雜度\(O(n)\)

class Solution {
public:
    int minCost(string s, vector<int>& cost) {
        int ans = 0, c = 0, m = 0;
        for(int i = 0; i < s.size(); i++) {
            if(i && s[i] != s[i - 1]) {
                ans += c - m;
                c = m = 0;
            }
            c += cost[i];
            m = max(m, cost[i]);
        }
        return ans + c - m;
    }
};

4. 保證圖可完全遍歷

並查集+貪心,時間複雜度\(O(n)\)

class Solution {
public:
    int find(int k, vector<int>& f) {
        return f[k] == k ? k : f[k] = find(f[k], f);
    }
    
    int maxNumEdgesToRemove(int n, vector<vector<int>>& edges) {
        int ans = 0;
        vector<int> f1(n + 1), f2(n + 1);
        for(int i = 1; i <= n; i++) f1[i] = i;
        for(int i = 0; i < edges.size(); i++) {
            if(edges[i][0] == 3) {
                int a = edges[i][1], b = edges[i][2];
                if(find(a, f1) != find(b, f1)) f1[f1[a]] = f1[b];
                else ans++;
            }
        }
        for(int i = 1; i <= n; i++) f2[i] = f1[i];
        for(int i = 0; i < edges.size(); i++) {
            int a = edges[i][1], b = edges[i][2];
            if(edges[i][0] == 1) {
                if(find(a, f1) != find(b, f1)) f1[f1[a]] = f1[f1[b]];
                else ans++;
            }
            else if(edges[i][0] == 2) {
                if(find(a, f2) != find(b, f2)) f2[f2[a]] = f2[f2[b]];
                else ans++;
            }
        }
        for(int i = 2; i <= n; i++) if(find(f1[i], f1) != find(f1[1], f1) || find(f2[i], f2) != find(f2[1], f2)) return -1;
        return ans;
    }
};