力扣第 411 场周赛题解

3258. 统计满足 K 约束的子字符串数量 I

给你一个 二进制 字符串 s 和一个整数 k

如果一个 二进制字符串 满足以下任一条件,则认为该字符串满足 k 约束

  • 字符串中 0 的数量最多为 k
  • 字符串中 1 的数量最多为 k

返回一个整数,表示 s 的所有满足 k 约束 

子字符串

的数量。

示例 1:

输入:s = "10101", k = 1

输出:12

解释:

s 的所有子字符串中,除了 "1010""10101" 和 "0101" 外,其余子字符串都满足 k 约束。

示例 2:

输入:s = "1010101", k = 2

输出:25

解释:

s 的所有子字符串中,除了长度大于 5 的子字符串外,其余子字符串都满足 k 约束。

示例 3:

输入:s = "11111", k = 1

输出:15

解释:

s 的所有子字符串都满足 k 约束。

提示:

  • 1 <= s.length <= 50
  • 1 <= k <= s.length
  • s[i] 是 '0' 或 '1'

题目说满足任意条件即可成立,也就是说两个条件同时都不满足时结果不成立.看到题目数据范围,我们可以采用暴力枚举每一种情况,时间复杂度O(n^2),可以过.

class Solution {
public:int countKConstraintSubstrings(string s, int k) {int count = 0;for (int i = 0; i < s.size(); i++) {int zeroCount = 0;int oneCount = 0;for (int j = i; j < s.size(); j++) {if (s[j] == '0') zeroCount++;if (s[j] == '1') oneCount++;if (zeroCount <= k || oneCount <= k) {count++;}}}return count;}
};

但是我们要想优化,可以考虑以下标0,1,2,3.....为右端点的子串个数统计出来,例如10101,以下标0为右端点的子串为1;以下标1为右端点的子串为0,10;以下标2为右端点的子串为101,01,1......以此类推,然后把这些所有子串个数都加起来就是答案,但是,例如1010101,k=2,枚举到下标为5,即101010,就不符合要求了,但可以把子串缩小,例如01010,就符合要求了,不难发现如果这个长度为5的子串符合要求,那么长度更短的子串也符合要求,所以比如说右端点为0时,左端点最远为第一个0的位置,左端点L=1,右端点R=5,那么从[L,R],[L+1,R].....到[R,R]都是符合的,一共R-L+1个数,把这些数的个数加到答案里面就可以了,同时,当右端点增大时,比如增大到末尾的1时,就不符合要求了,所以要将左端点增大,所以可以推出当右端点增大时,左端点要么不变,要么增大,符合滑动窗口的思想,时间复杂度O(n),n为字符串长度,L只会增加,不会减少,所以为O(n).

class Solution {
public:int countKConstraintSubstrings(string s, int k) {int cnt[2],l=0,ans=0;for(int i=0;i<s.size();i++){cnt[s[i]%2]++;while(cnt[0]>k&&cnt[1]>k)cnt[s[l++]%2]--;ans+=i-l+1;}return ans;}
};

3259. 超级饮料的最大强化能量

来自未来的体育科学家给你两个整数数组 energyDrinkA 和 energyDrinkB,数组长度都等于 n。这两个数组分别代表 A、B 两种不同能量饮料每小时所能提供的强化能量。

你需要每小时饮用一种能量饮料来 最大化 你的总强化能量。然而,如果从一种能量饮料切换到另一种,你需要等待一小时来梳理身体的能量体系(在那个小时里你将不会获得任何强化能量)。

返回在接下来的 n 小时内你能获得的 最大 总强化能量。

注意 你可以选择从饮用任意一种能量饮料开始。

示例 1:

输入:energyDrinkA = [1,3,1], energyDrinkB = [3,1,1]

输出:5

解释:

要想获得 5 点强化能量,需要选择只饮用能量饮料 A(或者只饮用 B)。

示例 2:

输入:energyDrinkA = [4,1,1], energyDrinkB = [1,1,3]

输出:7

解释:

  • 第一个小时饮用能量饮料 A。
  • 切换到能量饮料 B ,在第二个小时无法获得强化能量。
  • 第三个小时饮用能量饮料 B ,并获得强化能量。

提示:

  • n == energyDrinkA.length == energyDrinkB.length
  • 3 <= n <= 105
  • 1 <= energyDrinkA[i], energyDrinkB[i] <= 105

例如,[1,3,1]和 [3,1,1],题目中说每小时只能饮用一种能量饮料,且相邻的下标不能连续选择不同数组中的数,所以如果选定一个数组,可以连着选,但是选不同数组,只能跳着选.同时,题目保证所有数为正数,所以最后一个数一定要选(比如第一个数组,只选3和既选3又选1,肯定后者更优)  (因为题目给了两个数组a,b,从a数组选若干数,从b数组选若干数,相当于从两个数组中各选了一个子序列,所以对于子序列题目,可以考虑最后一个数是怎么选的),所以选了最后一个数之后,接下来分两种情况,要么选同一个数组中的倒数第二个数,要么跳着选另一个数组的倒数第三个数(不能隔两个数选下一个,因为结果不优),所以这道题本质就是选或不选的题,比如选完第一个数组的最后一个1之后,接下来选第一个数组中的3,转化为从[1,3],[3,1]的选择情况;接下来选第二个数组中的3,就转化为没有数字选了.所以需要两个变量,一个是用i表示从下标0到下标i的数,第二个是用j表示从第i个位置选的数是属于a数组还是b数组(j=0表示从a数组选,也就是选了ai;j=1表示从b数组选,也就是选了bi).用dfs(i,j)表示从下标[0,i]中选,且下标i选的数为a[i](j==0),或者b[i](j==1),所以就是dfs(i-1,j)和dfs(i-2,1-j),二者取最大值,定义数组c,将数组a和b放进c中(下标0就是a,1就是b),还要考虑如果i<0,结果就越界了,所以直接返回0,所以dfs(i,j)=max(dfs(i-1,j),dfs(i-2,1-j))+c[j][i].结果返回的就是max(dfs(n-1,0),dfs(n-1,1)).考虑到整个递归过程中有大量重复递归调用(递归入参相同),由于递归函数没有副作用,同样的入参无论计算多少次,算出来的结果都是一样的,因此可以用记忆化搜索来优化.(python直接加@cache).也可以把记忆化搜索翻译成递推,当i=0时,递归到-2,i的范围是从-2到n-1,有n+2个数,j就是0,1.把dfs(-2,j)翻译成f[0][j],dfs(-1,j)翻译成f[1][j],dfs(i,j)=max(dfs(i-1,j),dfs(i-2,1-j))+c[j][i]翻译成f[i+2][j]=max(f[i+1][j],f[i][1-j])+c[j][i].(如果把数组c中的i加上2后,当i=n-1时,就越界了,所以不能加2,还有就是仅仅是在f数组前面插入状态,没在c数组前插入状态,所以不改变c数组),答案为 max(f[n+1][0],f[n+1][1]).

class Solution {
public:long long maxEnergyBoost(vector<int>& a, vector<int>& b) {int n = a.size();vector<array<long long,2>>f(n + 2);for (int i = 0; i < n; i++) {f[i+2][0]=max(f[i+1][0],f[i][1])+a[i];f[i+2][1]=max(f[i+1][1],f[i][0])+b[i];}return max(f[n+1][0],f[n+1][1]);}
};

3260. 找出最大的 N 位 K 回文数

给你两个 正整数 n 和 k

如果整数 x 满足以下全部条件,则该整数是一个 k 回文数

  • x 是一个 回文数。
  • x 可以被 k 整除。

以字符串形式返回 最大的  n 位 k 回文数

注意,该整数 不 含前导零。

示例 1:

输入: n = 3, k = 5

输出: "595"

解释:

595 是最大的 3 位 k 回文数。

示例 2:

输入: n = 1, k = 4

输出: "8"

解释:

1 位 k 回文数只有 4 和 8。

示例 3:

输入: n = 5, k = 6

输出: "89898"

提示:

  • 1 <= n <= 105
  • 1 <= k <= 9

在i位置填了数字a,也同时在n-1-i位置填了数字a,在生成答案之前,只需考虑回文数%k的结果,例如三位数,中间位置初始化为0,则有9种情况(题目说不含前导零):101,202,.....909,接下来考虑每一个数中间填0~9又有10种情况,仅仅是三位数就有这么多种情况,如何减少考虑的数字的数量?这里有一个数学公式:(a+b)%k=(a%k+b%k)%k------取模恒等式,就是不用把整个数字生成出来去看%k的结果,可以在生成数字过程中直接%k.用i表示当前填到数字的哪一位,用j表示填的数字%k的结果.一开始为(0,0),当i=m时表示所有数都填好了(m=n/2上取整,比如一个6位数,从右到左i依次取0,1...5,当i=2时,还没填好,当i=3时,所有数字都填好了,比如一个5位数,i=2时继续填,i=3时填好了),即从起点(0,0)--->终点(m,0),m=n/2上取整.期间状态为从(1,(9*10的n-1次方+9)%k).....到(1,(1*10的n-1次方+1)%k),又可以递归到(i+1,....)...可以将题目考虑为图论问题,就是经过一些点最后到达终点,路径可以表示出填哪些数字,就是dfs暴搜加上vis数组记录访问过的结点.

class Solution {
public:
bool dfs(int i,int j,int n,int k,int m,vector<int>& pow10,string& ans,vector<vector<int>>&vis){if(i==m) return j==0;vis[i][j]=true;for (int d=9;d>=0;d--){ int j2;if(n%2&&i==m-1){ j2=(j+d*pow10[i])%k;}else{j2=(j+d*(pow10[i]+pow10[n-1-i]))%k;}if(!vis[i+1][j2]&&dfs(i+1,j2,n,k,m,pow10,ans,vis)){ans[i]=ans[n-1-i]='0'+d;return true;}}return false;
}
string largestPalindrome(int n,int k){vector<int>pow10(n);pow10[0]=1;for(int i=1;i<n;i++){pow10[i]=pow10[i-1]*10%k;}string ans(n,0);int m=(n+1)/2;vector<vector<int>>vis(m+1,vector<int>(k));dfs(0,0,n,k,m,pow10,ans,vis);return ans;}
};

3261. 统计满足 K 约束的子字符串数量 II

给你一个 二进制 字符串 s 和一个整数 k

另给你一个二维整数数组 queries ,其中 queries[i] = [li, ri] 。

如果一个 二进制字符串 满足以下任一条件,则认为该字符串满足 k 约束

  • 字符串中 0 的数量最多为 k
  • 字符串中 1 的数量最多为 k

返回一个整数数组 answer ,其中 answer[i] 表示 s[li..ri] 中满足 k 约束的子字符串的数量。

示例 1:

输入:s = "0001111", k = 2, queries = [[0,6]]

输出:[26]

解释:

对于查询 [0, 6], s[0..6] = "0001111" 的所有子字符串中,除 s[0..5] = "000111" 和 s[0..6] = "0001111" 外,其余子字符串都满足 k 约束。

示例 2:

输入:s = "010101", k = 1, queries = [[0,5],[1,4],[2,3]]

输出:[15,9,3]

解释:

s 的所有子字符串中,长度大于 3 的子字符串都不满足 k 约束。

提示:

  • 1 <= s.length <= 105
  • s[i] 是 '0' 或 '1'
  • 1 <= k <= s.length
  • 1 <= queries.length <= 105
  • queries[i] == [li, ri]
  • 0 <= li <= ri < s.length
  • 所有查询互不相同

此题和第一题不同在于本题是要求子串中有多少个合法的子串,用Left[i]表示以i为右端点的子串通过滑动窗口求出的Left的位置,例如,一子串范围为[L,R],如果这个范围里所有的Left[i]都在L的左边,那么这里面所有子串都符合要求,长度为m的子串有1+2+3+...+m=(m+1)*m/2个子串,如果某个子串中有指向外面的,也有指向里面的,如果右端点指向的Left[i]在询问的区间内,那么直接可以把r-l+1加到答案里面,不难发现,每个位置都对应一个r-l+1,可以理解为关于r-l+1的子数组的和,就可以用前缀和优化.所以该题就分为两种情况:找一个位置,在这个位置左边所有子串全部都是合法的,直接用等差数列之和,在这个位置右边的子串,用前缀和算出来,所以回答每次询问,就取决于能不能快速找到分界位置,因为滑动窗口的左端点是不断向右移动的,所以这个Left数组是一个有序数组,可以在这个有序数组中二分找到大于等于L第一个位置作为分界位置.

class Solution {
public:vector<long long> countKConstraintSubstrings(string s, int k, vector<vector<int>>& queries) {int n=s.length(),m=queries.size();vector<int>left(n);vector<long long>sum(n+1);int cnt[2]{},l=0;for (int i=0;i<n;i++){cnt[s[i]%2]++;while(cnt[0]>k&&cnt[1]>k){cnt[s[l++]%2]--;}left[i]=l;// 计算 i-left[i]+1 的前缀和sum[i+1]=sum[i]+i-l+1;}vector<long long>ans(m);for (int i=0;i<m;i++){int l=queries[i][0],r=queries[i][1];int j=lower_bound(left.begin()+l,left.begin()+r+1,l)-left.begin();ans[i]=sum[r+1]-sum[j]+(long long)(j-l+1)*(j-l)/2;}return ans;}
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/51986.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【数据结构-哈希前缀】力扣2845. 统计趣味子数组的数目

给你一个下标从 0 开始的整数数组 nums &#xff0c;以及整数 modulo 和整数 k 。 请你找出并统计数组中 趣味子数组 的数目。 如果 子数组 nums[l…r] 满足下述条件&#xff0c;则称其为 趣味子数组 &#xff1a; 在范围 [l, r] 内&#xff0c;设 cnt 为满足 nums[i] % mod…

JVM -垃圾回收器

本人在这篇文章中讲解了垃圾回收机制&#xff0c;这为前置知识 美团一面面经&#xff1a;Threadlocal&#xff08;线程局部变量的原理&#xff09;-&#xff1e;内存泄漏问题-&#xff1e;垃圾回收机制_threadlocal回收-CSDN博客 首先对前置知识漏洞做一个补充&#xff1a;ja…

open Euler22.03系统安装宝塔面板

环境&#xff1a;华为云open Euler22.03操作系统 配置&#xff1a;2核4G 1、安装宝塔面板。 登录弹性云服务器。 执行以下命令&#xff0c;下载并安装宝塔面板。 yum install -y wget && wget -O install.sh http://download.bt.cn/install/install_6.0.sh &&…

STM32裸机和RTOS中的线程安全问题及STM32cubeMX中的线程安全策略

STM32线程安全问题 术语“线程” 和“多线程” 适用于裸机和基于RTOS的应用程序&#xff0c;线程安全问题并不只存在于基于RTOS的应用程序中&#xff1b;裸机应用程序中也存在这个问题&#xff0c;在裸机应用程序中&#xff0c;中断服务程序允许调用C库函数。线程安全问题可能…

Python实现水果忍者(开源)

一、整体介绍&#xff1a; 1.1 前言&#xff1a; 游戏代码基于Python制作经典游戏案例-水果忍者做出一些改动&#xff0c;优化并增加了一些功能。作为自己Python阶段学习的结束作品&#xff0c;文章最后有源码链接。 1.2 Python主要知识&#xff1a; &#xff08;1&#xf…

Python爬虫——爬取某网站的视频

爬取视频 本次爬取&#xff0c;还是运用的是requests方法 首先进入此网站中&#xff0c;选取你想要爬取的视频&#xff0c;进入视频播放页面&#xff0c;按F12&#xff0c;将网络中的名称栏向上拉找到第一个并点击&#xff0c;可以在标头中&#xff0c;找到后续我们想要的一些…

qt-15综合实例(电子时钟)-多态重写鼠标单击和移动事件

综合实例-电子时钟 知识点digiclock.hdigiclock.cppmain.cpp运行图 知识点 setWindowOpacity(0.5);//设置窗体透明度 QTimer* Timer new QTimer(this);//新建一个定时器 connect(Timer,SIGNAL(timeout()),this,SLOT(ShowTime())); Timer->start(1000);//启动定时器 digic…

稚晖君发布5款全能人形机器人,开源创新,全能应用

8月18日&#xff0c;智元机器人举行“智元远征 商用启航” 2024年度新品发布会&#xff0c;智元联合创始人彭志辉主持并发布了“远征”与“灵犀”两大系列共五款商用人形机器人新品——远征A2、远征A2-W、远征A2-Max、灵犀X1及灵犀X1-W&#xff0c;并展示了在机器人动力、感知、…

猫头虎分享:练习提示词Prompt有什么好方法?提高Prompt水平和质量

猫头虎是谁&#xff1f; 大家好&#xff0c;我是 猫头虎&#xff0c;别名猫头虎博主&#xff0c;擅长的技术领域包括云原生、前端、后端、运维和AI。我的博客主要分享技术教程、bug解决思路、开发工具教程、前沿科技资讯、产品评测图文、产品使用体验图文、产品优点推广文稿、…

深扒大模型微调密码 - 从入门到技术小白都能看懂的神操作

朋友们&#xff0c;你们有没有听说过"大模型"和"微调"这两个概念呢&#xff1f;别着急,我们今天就来好好聊一聊! 想象一下,你有一个非常勤奋的小助理,它会尽最大努力帮你完成各种任务。不过有时候,它的知识储备和能力肯定有限,所以你得适时给它一些专门的…

树莓派5 笔记25:第一次启动与配置树莓派5_8G

今日继续学习树莓派5 8G&#xff1a;&#xff08;Raspberry Pi&#xff0c;简称RPi或RasPi&#xff09; 本人所用树莓派4B 装载的系统与版本如下: 版本可用命令 (lsb_release -a) 查询: Opencv 与 python 版本如下&#xff1a; 今日购得了树莓派5_8G版本&#xff0c;性能是同运…

springboot航班进出港管理系统--论文源码调试讲解

第2章 开发环境与技术 本章节对开发航班进出港管理系统管理系统需要搭建的开发环境&#xff0c;还有航班进出港管理系统管理系统开发中使用的编程技术等进行阐述。 2.1 Java语言 Java语言是当今为止依然在编程语言行业具有生命力的常青树之一。Java语言最原始的诞生&#xff…

SQL每日一练-0815

今日SQL题难度&#xff1a;&#x1f31f;☆☆☆☆☆☆☆☆☆ 1、题目要求 计算每个产品类别在每个月的总销售额和总销量。找出每个月销售额最高的产品类别&#xff0c;显示类别名称、销售月份、总销售额和总销量。 2、表和虚拟数据 现有两个表&#xff1a;Products 和…

牛客网习题——通过C++实现

一、目标 实现下面4道练习题增强C代码能力。 1.求123...n_牛客题霸_牛客网 (nowcoder.com) 2.计算日期到天数转换_牛客题霸_牛客网 (nowcoder.com) 3.日期差值_牛客题霸_牛客网 (nowcoder.com) 4.打印日期_牛客题霸_牛客网 (nowcoder.com) 二、对目标的实现 1.求123...n_…

[机器学习]--KNN算法(K邻近算法)

KNN (K-Nearest Neihbor,KNN)K近邻是机器学习算法中理论最简单,最好理解的算法,是一个 非常适合入门的算法,拥有如下特性: 思想极度简单,应用数学知识少(近乎为零),对于很多不擅长数学的小伙伴十分友好虽然算法简单,但效果也不错 KNN算法原理 上图是每一个点都是一个肿瘤病例…

Sakana.ai 迈向完全自动化的开放式科学发现

每周跟踪AI热点新闻动向和震撼发展 想要探索生成式人工智能的前沿进展吗&#xff1f;订阅我们的简报&#xff0c;深入解析最新的技术突破、实际应用案例和未来的趋势。与全球数同行一同&#xff0c;从行业内部的深度分析和实用指南中受益。不要错过这个机会&#xff0c;成为AI领…

从零开始搭建k8s集群详细步骤

声明&#xff1a;本文仅作为个人记录学习k8s过程的笔记。 节点规划&#xff1a; 两台节点为阿里云ECS云服务器&#xff0c;操作系统为centos7.9&#xff0c;master为2v4GB,node为2v2GB,硬盘空间均为40GB。&#xff08;节点基础配置不低于2V2GB&#xff09; 主机名节点ip角色部…

Docker最佳实践进阶(一):Dockerfile介绍使用

大家好&#xff0c;上一个系列我们使用docker安装了一系列的基础服务&#xff0c;但在实际开发过程中这样一个个的安装以及繁杂命令不仅仅浪费时间&#xff0c;更是容易遗忘&#xff0c;下面我们进行Docker的进阶教程&#xff0c;帮助我们更快速的部署和演示项目。 一、什么是…

力扣面试经典算法150题:找出字符串中第一个匹配项的下标

找出字符串中第一个匹配项的下标 今天的题目是力扣面试经典150题中的数组的简单题: 找出字符串中第一个匹配项的下标 题目链接&#xff1a;https://leetcode.cn/problems/find-the-index-of-the-first-occurrence-in-a-string/description/?envTypestudy-plan-v2&envIdto…

docker compose部署rabbitmq集群,并使用haproxy负载均衡

一、创建rabbitmq的data目录 mkdir data mkdir data/rabbit1 mkdir data/rabbit2 mkdir data/rabbit3 二、创建.erlang.cookie文件&#xff08;集群cookie用&#xff09; echo "secretcookie" > .erlang.cookie 三、创建haproxy.cfg配置文件 global log stdout fo…