# 768. Max Chunks To Make Sorted II

对给定数组分partition，要求每个partition的数字刚好是对数组排序后落在这些位置的数字，问最多能分几个partitions。max+partition最直接的想法就是DP，但这道题有更快和简便的做法，两种解法分别利用了这道题的两个性质。1. expected = sorted(nums), 那么nums\[i,j]能被分到一个partition <=> sum(expected\[i, j]) == sum(nums\[i, j])。用反证法可以证明，这里就不赘述了。

```cpp
/*
 * @lc app=leetcode id=768 lang=cpp
 *
 * [768] Max Chunks To Make Sorted II
 */

// @lc code=start
class Solution {
public:
    int maxChunksToSorted(vector<int>& arr) {
        const int N = arr.size();
        vector<int> expected(arr);
        sort(expected.begin(), expected.end());
        int res = 0;
        long sum = 0, sum2 = 0;
        for (int i = 0; i < N; ++i) {
            sum += arr[i];
            sum2 += expected[i];
            if (sum == sum2) ++res;
        } 
        return res;
    }
};
// @lc code=end

```

2\. nums\[i, j]能分成一个partition <=> j之后不会有元素比nums\[i , j]中最大的数小。因此对每个i先统计从前面遍历过来当前最大值，且统计从后面遍历过来的当前最小值，然后对每个i看从前面过来的最大是否小于后面过来的最小。

```cpp
/*
 * @lc app=leetcode id=768 lang=cpp
 *
 * [768] Max Chunks To Make Sorted II
 */

// @lc code=start
class Solution {
public:
    int maxChunksToSorted(vector<int>& arr) {
        const int N = arr.size();
        vector<int> f(arr), b(arr);
        for (int i = 1; i < N; ++i) f[i] = max(f[i - 1], arr[i]);
        for (int i = N - 2; i >= 0; --i) b[i] = min(b[i + 1], arr[i]);
        int res = 1;
        for (int i = 0; i < N - 1; ++i) {
            if (f[i] <= b[i + 1]) ++res;
        } 
        return res;
    }
};
// @lc code=end

```

解法参考自[这](https://link.zhihu.com/?target=https%3A//www.cnblogs.com/grandyang/p/8850299.html)。
