持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第14天,点击查看活动详情
前言
今天的题目为中等,题目为简单的动态规划题目,主要是需要我们能够设计一个算法来统计所有可行的思路中,哪个是更优的。
每日一题
今天的题目是 926. 将字符串翻转到单调递增,难度为中等
-
如果一个二进制字符串,是以一些 0(可能没有 0)后面跟着一些 1(也可能没有 1)的形式组成的,那么该字符串是 单调递增 的。
-
给你一个二进制字符串 s,你可以将任何 0 翻转为 1 或者将 1 翻转为 0 。
-
返回使 s 单调递增的最小翻转次数。
示例 1:
输入:s = "00110"
输出:1
解释:翻转最后一位得到 00111.
示例 2:
输入:s = "010110"
输出:2
解释:翻转得到 011111,或者是 000111。
示例 3:
输入:s = "00011000"
输出:2
解释:翻转得到 00000000。
提示:
- 1 <= s.length <= 105
- s[i] 为 '0' 或 '1'
题解
动态规划
对于题目的要求,我们可以定义一下碰到1的时候不去反转它,再碰到0的时候,就会出现两种情况,一种是将当前的0反转变成1另一种是将当前的0之前碰到的1都反转变成0,所以我们需要两个数来记录下这些数据,用于判断在碰到一个0的时候,那种做法是更佳的。
首先我们定义一个 one 参数用于纪录下当前的 1 的数量,并且在碰到 0 的时候,我们会有着两种选择,一种是将这个 0 前面的所有的 1 都反转为 0 另一种是将当前的 0 反转为 1,我们可以在定一个参数,用于确认当前这两种方法哪个的反转次数最少,将它纪录下来,在下一次碰到 0 的时候,还是这样去计算,知道最后就可以得到答案了。
function minFlipsMonoIncr(s: string): number {
let res = 0;
let one = 0;
for(let i=0;i<s.length;i++){
if(s[i].charAt(0) == '1'){
one++
}else {
res = Math.min(res+1,one)
}
}
return res
};