差分数组

64 阅读2分钟

​携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第23天,点击查看活动详情

差分数组

差分数组https://labuladong.github.io/algo/2/20/25/

例题1

1109. 航班预订统计 - 力扣(LeetCode)

代码:

class Solution {
public:
//差分数组的话那必然在[l,r] 都加上一个数c  <=> nums[l] += c && nums[r + 1] -= c
//如果求出了差分数组,则通过相加可得原数组   c为(差分值) = ret[i] - ret[i - 1], 若要得原数组,则 c(差分值) + ret[i - 1]  (准确的说是求差分的前缀和)
    vector<int> corpFlightBookings(vector<vector<int>>& bookings, int n) {
        vector<int>ret(n,0);                //差分数组
        for (int i = 0; i < bookings.size(); i++) {
            int a = bookings[i][0], b = bookings[i][1], c = bookings[i][2];
            ret[a - 1] += c;
            if (b < n) {
                ret[b] -= c;
            }
            
        }
        for (int i = 1; i < n; i++) {    //求差分的前缀和
            ret[i] += ret[i - 1];
        }
        return ret;
    }
};

例题2

6158. 字母移位 II - 力扣(LeetCode)

6158. 字母移位 II

难度中等6

给你一个小写英文字母组成的字符串 s 和一个二维整数数组 shifts ,其中 shifts[i] = [starti, endi, directioni] 。对于每个 i ,将 s 中从下标 starti 到下标 endi (两者都包含)所有字符都进行移位运算,如果 directioni = 1 将字符向后移位,如果 directioni = 0 将字符向前移位。

将一个字符 向后 移位的意思是将这个字符用字母表中 下一个 字母替换(字母表视为环绕的,所以 'z' 变成 'a')。类似的,将一个字符 向前 移位的意思是将这个字符用字母表中 前一个 字母替换(字母表是环绕的,所以 'a' 变成 'z' )。

请你返回对 s 进行所有移位操作以后得到的最终字符串。

 

示例 1:

输入: s = "abc", shifts = [[0,1,0],[1,2,1],[0,2,1]]
输出: "ace"
解释: 首先,将下标从 0 到 1 的字母向前移位,得到 s = "zac" 。
然后,将下标从 1 到 2 的字母向后移位,得到 s = "zbd" 。
最后,将下标从 0 到 2 的字符向后移位,得到 s = "ace"

示例 2:

输入: s = "dztz", shifts = [[0,0,0],[1,1,1]]
输出: "catz"
解释: 首先,将下标从 0 到 0 的字母向前移位,得到 s = "cztz" 。
最后,将下标从 1 到 1 的字符向后移位,得到 s = "catz"

代码

class Solution {
public:
    string shiftingLetters(string s, vector<vector<int>>& shifts) {
        int n = s.size();
        vector<int> f(n + 1, 0);
        for (int i = 0; i < shifts.size(); i++) {
            int start = shifts[i][0], mid = shifts[i][1], end = shifts[i][2];
            if (end == 0) {f[start]--; f[mid + 1]++;}
            else {f[start]++; f[mid + 1]--;}
        }

        for (int i = 1; i < f.size(); i++) {
            f[i] = f[i] + f[i - 1];
        }

        string ans;
        for (int i = 0; i < n; i++) {
            // cout << f[i] << "";
            char c = s[i];
            int d = (c - 'a' + f[i]) % 26;
            char m = (d + 26) % 26 + 'a';             //因为会出现负数,所以才让d 加 26 ,否则只有上一步就行。
            ans.push_back(m);
        }

        return ans;
    }
};

\