跳转至

3191. 使二进制数组全部等于 1 的最少操作次数 I

题目描述

给你一个二进制数组 nums 。

你可以对数组执行以下操作 任意 次(也可以 0 次):

  • 选择数组中 任意连续 3 个元素,并将它们 全部反转 。

反转 一个元素指的是将它的值从 0 变 1 ,或者从 1 变 0 。

请你返回将 nums 中所有元素变为 1 的 最少 操作次数。如果无法全部变成 1 ,返回 -1 。

 

示例 1:

输入:nums = [0,1,1,1,0,0]

输出:3

解释:
我们可以执行以下操作:

  • 选择下标为 0 ,1 和 2 的元素并反转,得到 nums = [1,0,0,1,0,0] 。
  • 选择下标为 1 ,2 和 3 的元素并反转,得到 nums = [1,1,1,0,0,0] 。
  • 选择下标为 3 ,4 和 5 的元素并反转,得到 nums = [1,1,1,1,1,1] 。

示例 2:

输入:nums = [0,1,1,1]

输出:-1

解释:
无法将所有元素都变为 1 。

 

提示:

  • 3 <= nums.length <= 105
  • 0 <= nums[i] <= 1

解法

方法一:顺序遍历 + 模拟

我们注意到,数组中的第一个为 $0$ 的位置,一定需要进行一次反转操作,否则无法将其变为 $1$。因此,我们可以顺序遍历数组,每次遇到 $0$,就将其后两个元素进行反转操作,累计一次操作次数。

遍历结束后,返回答案即可。

时间复杂度 $O(n)$,其中 $n$ 为数组 $\textit{nums}$ 的长度。空间复杂度 $O(1)$。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
class Solution:
    def minOperations(self, nums: List[int]) -> int:
        ans = 0
        for i, x in enumerate(nums):
            if x == 0:
                if i + 2 >= len(nums):
                    return -1
                nums[i + 1] ^= 1
                nums[i + 2] ^= 1
                ans += 1
        return ans
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
class Solution {
    public int minOperations(int[] nums) {
        int ans = 0;
        int n = nums.length;
        for (int i = 0; i < n; ++i) {
            if (nums[i] == 0) {
                if (i + 2 >= n) {
                    return -1;
                }
                nums[i + 1] ^= 1;
                nums[i + 2] ^= 1;
                ++ans;
            }
        }
        return ans;
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
class Solution {
public:
    int minOperations(vector<int>& nums) {
        int ans = 0;
        int n = nums.size();
        for (int i = 0; i < n; ++i) {
            if (nums[i] == 0) {
                if (i + 2 >= n) {
                    return -1;
                }
                nums[i + 1] ^= 1;
                nums[i + 2] ^= 1;
                ++ans;
            }
        }
        return ans;
    }
};
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
func minOperations(nums []int) (ans int) {
    for i, x := range nums {
        if x == 0 {
            if i+2 >= len(nums) {
                return -1
            }
            nums[i+1] ^= 1
            nums[i+2] ^= 1
            ans++
        }
    }
    return
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
function minOperations(nums: number[]): number {
    const n = nums.length;
    let ans = 0;
    for (let i = 0; i < n; ++i) {
        if (nums[i] === 0) {
            if (i + 2 >= n) {
                return -1;
            }
            nums[i + 1] ^= 1;
            nums[i + 2] ^= 1;
            ++ans;
        }
    }
    return ans;
}

评论