自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(84)
  • 收藏
  • 关注

原创 【无标题】

最近都到AcWing发博客去啦。

2022-11-10 20:28:22 219 1

原创 一道dp的三次优化(时间+空间)

首先说一下代码里的两层循环为什么可以互换位置,循环换一下顺序,不影响结果,是因为只要保证计算某个状态时候,被转移的状态全部计算过了就行,这个题目,换一下两维枚举顺序,显然可以保证这一点。,第二维只会从j和j-1,那就考虑优化他们了。f[i][j]表示到达第i个点的时候,一共走了j步,这样的dp方程的转移非常好想,直接考虑j - 1步的时候能从哪些位置转移过来就好了。很像完全背包的转移方程的优化,关于完全背包,依稀记得他的n3优化到n2的推理,在白书上有,进阶指南没写这部分优化,有点子可惜。...

2022-08-05 23:52:55 292 1

原创 2022牛客多校第二场的J -- 三分做法

三分的值是公差d,想要求出方差,还差个首项。代入d到式子里去,然后展开一下,发现是个二次函数,这样就能确定最优的首项a1的值是多少了。于是细细优化了一下推的式子,能用int的都用int了,然后尽量减少除法的使用次数。赛时百度了线性回归的公式抄过去了,但是听说三分也能做,于是来写一下三分的做法。然后随便写了写,结果被卡精度了。...

2022-07-25 23:31:45 233

原创 确定括号序列中的一些位置

的数量,sum为左括号数量-右括号数量。当sum+cnt==1时,可以确定这cnt个?这时候只需要清空cnt,然后让sum=1。最后,如果cnt==sum,说明最终剩下的这cnt个?必须为),也就是此时可以输出YES了。给定括号序列,其中一些位置是未知的,如果这些未知的位置能够确定填什么,那就YES,否则NO。...

2022-07-22 16:08:49 184

原创 棋盘左上角到右下角方案数(2)

1.从左上角(1,1)到右下角(n,m)的方案数是C(n + m - 2, n - 1)2.左上角到右下角的方案数之和是 C(n + m - 1, n)- 13.第n行的和是C(n + m - 1, n)第三点的证明,可以看E题的题解Codeforces Global Round 21 A-E - kilo的文章 - 知乎...

2022-06-27 00:17:44 214

原创 B-杰哥的树(状压树形dp)

武汉科技大学第十一届程序设计校赛——B-杰哥的树

2022-06-06 23:53:56 127

原创 C. Binary String(推式子)

链接:Educational Codeforces Round 128 (Rated for Div. 2) - C题意:给定字符串s,可以从开头删去一部分,还可以从末尾删除一部分,求这个式子最小值:max (删去的1个数,剩下的0个数)。做法:设剩下的子串,左端点为,右端点为。是前缀和,意思是前缀中1的个数。删去的1:剩下的0:很显然后面那部分是相同的,所以可以分类讨论前面的式子。若:则 要最大化,且与的距离不超过,的物理意义是,剩下的串中1的个数,显然与的距离越

2022-05-14 16:51:11 664

原创 G-多吃蘑菇(树形dp)

G-多吃蘑菇题意:给定一棵树,树上的节点有颜色与权值,求一条简单路径,路径上的权值和最大,同颜色只能统计一次。做法:从根节点开始往下遍历,同时维护一个数组,表示从当前节点到根的路径上,出现过的颜色的最大值。很明显节点可能会更新这个数组,更新完后,可以继续往下dfs,当以为根的子树遍历完后,对数组的贡献可以取消了就。代码:(比赛时的代码,用了map来代替)#include <bits/stdc++.h>#define int long longusing namesp

2022-05-09 22:43:06 260

原创 区间修改矩阵与查询(树状数组)

例题:题意:给定矩阵大小,一开始全部元素都为0。操作1将一块区域取反;操作2回答区域有多少个1.做法:树状数组维护二维差分,将区间操作变为单点操作。是差分数组。差分数组的前缀和就是单点的值,而这里求的是区间的值,那就是差分数组前缀和后,变为单点的值,单点的前缀和才是区间的值。就是下面这个式子了。这个式子的意思是的前缀和。为了方便维护,拆分为这四个式子。类比一维的树状数组,表示右端点为,长为的区间和。二维的那就是,表示右下角为,高,宽的区间的区间和。所以树状数组也就

2022-05-09 22:17:13 327

原创 Codeforces Round #789 (Div. 2)

D. Tokitsukaze and Meeting题意:给定一个01字符串s,代表着一群学生。接下来他们会按顺序进入的矩阵,新进入的会留在,已经进入的推后。问第 i 个学生进入后,矩阵的有多少行含1,有多少列含1。做法:表示第个学生进入后,矩阵有多少行含1。很明显,可以由转移而来,再判定以结尾的这一段长为的区间是否含1即可。对于列,手画一下矩阵,发现总是只有那一列在变化,其他的都没有改变过,所以直接开一个数组简单维护一下即可。char s[N];int f[N],

2022-05-09 21:03:11 423

原创 牛客小黑月赛 F - 孤独的树

链接:F - 孤独的树题意:给定一棵树,每次操作可以消去一个节点权值的质因子,求最小操作次数,使得树上相邻节点互质。做法:质因子之间互不影响,所以是可以分开看的。如果只考虑消去某个质因子 k ,d[i][0]为不操作这个节点,使得其与子节点互质,d[i][1]为操作这个节点,使得与子节点互质。就有转移方程:d[x][0] += d[y][1];d[x][1] += min(d[y][0], d[y][1]);d[x][1] += calc(a[x], k);从1~n遍历所有节点,如果a

2022-04-26 17:12:43 221

原创 区间的交集与差分的应用

这类题有两种形式:一:给定长度len,再给定m条线段。在总区间 [ 1, N ]上,如果一个长度为len的区间被一条线段覆盖,那么他权值+1,对于所有长度为len的区间,求最大的权值。解法:设 f [ i ] 为以 i 结尾的长度为len的区间权值,f 数组可以用差分维护。对于一条线段 L R,如果线段长度 >= len,显然这条线段对 f 数组是有贡献的,则 f 数组就要区间 【L + len - 1,R】+ 1。差分能快速的实现这个区间加的操作。例题:金牌厨师Solution:二分区

2022-04-26 15:57:32 232

原创 D. Progressions Covering

链接:D. Progressions Covering题意:给定数组b,数组a一开始全部都是0,对数组a可以每次选定一个长为k的区间,区间加上一个公差为1,首项为1的等差数列。问最少操作几次,可以使数组a[i]>=b[i]。做法:线段树维护区间加等差数列。两个懒标记,一个首项,一个公差。从数组a最后一个<b的数开始,以他为右端点开始区间加,这样一定最优。只一个懒标记的是线段树维护差分数组,区间加等差数列,变成差分数组L加首项,L+1~R区间加公差,R+1-=刚刚加的值。这里放上一

2022-04-16 11:55:49 386

原创 浙大城市学院校赛补题

Guaba and Computational Geometry题意:坐标轴上给定n个矩形,每个矩形都有自己的权值,求两个不相交矩形的权值之和的最大值。做法:两个矩形相交,则x轴投影和y轴投影都会相交。那就变成了在某个轴上的线段相交问题了,线段按照左端点排序之后,对于当前线段,求右端点小于他,且权值最大线段。最大权值用一个变量维护就行。#include <bits/stdc++.h>#define int long longusing namespace std;const in

2022-04-16 11:41:31 238

原创 F缆车(lca + 树形dp)

链接:F-缆车题意:给定一棵树,树根是1,树的边都是单向边。再给定树上的m个点和点K,现在可以从K连一条边到某个点,求连接完后K到这m个点的最小路径和。做法:求一下k点与这m个点的lca,如果这些点的lca不是k,那k必然连向那m个点的lca,k可能在这m个点之中,也可能不在,这个在细节上注意下就行。如果lca是k,那就枚举k向k的所有儿子连边,看哪种情况路径和最小就行了。#include <bits/stdc++.h>#define int long longusing na

2022-04-16 11:18:03 177

原创 “华为杯“ 武汉大学21级新生程序设计竞赛(补题)

和谐之树 · 改题意:给定n,设p为对区间【1,n】建线段树的时候的最大编号,对于所有的k ∈【L,R】,求【1,K】的最大编号之和。做法:稍微提一下对于区间【1,K】的最大区间之和,首先找到2的最高幂次cnt < K,求出K与 pow(2,cnt + 1)的差c,通过画图得知c对剩余编号的影响。很显然这个答案具有单调性,二分打表处理一下发现1 ~ 1e18中最大编号只有1850个。所以可以预处理一下这1850个区间前缀和,然后二分logn的查询sum(l - 1) 与sum( r ),就能

2022-04-04 21:46:20 456

原创 最近遇到的三道字典树问题

链接:A + B Problem agin数字A + 数字B不进位,对于每个数字求相加最大的结果。字典树的异或的板子题是不进位求a[i] ^ a[j] 最大,这题也类似。只是多了一个删除数字的操作,因为要避免同一个数字加两次。关于删除,只需要在插入的时候有计数的数组val[p]++,意味着当前这个节点有一个字符,删除的时候,val[p] += add,add为1或-1,就能实现这个删除之后又更新的操作了。#include <bits/stdc++.h>#define int long

2022-04-02 17:13:37 440

原创 Codeforces Round #780 (Div. 3)

Get an Even String给定字符串s,定义偶数串为相邻两个字符相同。比如aabb是,aaabb不是。求字符串s最少删多少个字符,使得s变成偶数串。直接考虑怎么删不好做,考虑剩下来的怎么样能最长,就知道删的数量最小是多少少了。可以dp求解这个最长偶数序列是多少。f[i][1]表示以字符a[i]结尾链接了一个最长偶数串的长度。f[i][0]表示以字符a[i]结尾的偶数串的长度。状态转移只需要知道字符a[i]上一次出现的位置即可。可以用map做,也可以开一个pos[N][26]的数组。

2022-04-02 11:32:47 523

原创 CCPC- 网赛重赛(补题)

Monopoly小兔子喜欢按照数组的顺序走,走到a[i]会得到a[i]点分数,如果走到n,会回到1。问小兔子得到分数x最少需要走几步。做法:设其走k圈零t步。则sum[n] * k + sum[t] == x。则对前缀和数组对sum[n]取模,用map映射之后同余的值放入vector即可二分搜索查询了。坑点:1.由于答案比较大,ans最好初始化1e18.2.正负数对sum[n]取模得到的结果并不一样,所以要 + sum[n] 再 % sum[n]。#include <bits/stdc+

2022-04-02 11:19:21 362

原创 文远知行杯广东工业大学第十六届程序设计竞赛

A-区间最大值定义 a[i] = n % i,给定L, R,求区间LR中,数组a的最大值。n <= 1e8.做法:如果n <= 1e6,可以建st表查询。注意到询问的次数才1e4,可以考虑下整除分块。本地打表分块,输出一个块内所有n % i的值,发现块内的左端点的n % i的值是最大的。从L开始到R进行整除分块的操作,不断更新最大值就好了。#include <bits/stdc++.h>#define int long longusing namespace std;

2022-03-29 00:34:23 550

原创 会写但是踩坑了的两题

值钱的项链一个环,环上每个点有两种选择,蓝色或红色,都有不同的价值,要求不能两个连着的红色。很容易想到:f[i][0] = max(f[i - 1][0], f[i - 1][1]) + v[i][0].val;f[i][1] = f[i - 1][0] + v[i][1].val;然后第一个点设置红色和蓝色,跑两次dp就出答案了。坑点:蓝(无) 蓝(有) 蓝(有)红(有) 红(有,很大)这样第三个蓝如果继承了第二个红,那就出问题了。有两种方法,一种是d

2022-03-24 15:37:57 362

原创 拆拆(质因子筛+枚举)

链接:拆拆一开始想的是预处理出1e6内所有数的质因子,然后,对于y个空位就不会排列组合了。。准备用多重集容斥原理什么的乱搞,,但是还是很容易发现会TLE。做法:对于数X的多种质因子,先只放其中一种到y个盒子里去就好了,剩下的继续放,互相是不影响的,而同种质因子放进y个盒子很显然是多重集的组合数的结论。于是这题就结束了。筛出1e6内所有数的质因子,快的做法就是线性筛出所有数的最小质因子,然后对于每个数,不断地除以最小质因子,就出结果了。#include <bits/stdc++.h>#

2022-03-23 20:46:51 437

原创 D. For Gamers. By Gamers.

调和级数枚举+二分查询。现在有m只怪兽要杀死,给定n种可选择的士兵,每次选择一种,同种士兵可以选多个。当士兵的攻击力之和大于怪兽的攻击力时,就可以杀死怪兽。每种士兵的雇用价格不一样,请你决定杀死当前怪兽的最小花费(不得超过C金币)。做法:定义f[i]为花费i元能得到的最大攻击力,若j是i的倍数,则花费j元可以得到攻击力f[i] * j / i。所以可以调和级数枚举这个dp的过程。调和级数结束之后,f[i] = max(f[i],f[i-1)),保证整个数组连续递增,便于二分查询。#include &l

2022-03-23 10:43:20 1153 3

原创 n个数选出m个字典序最小

从序列 N 个数中顺序选出 M 个不同的数, 使得这 M 个数的字典序最小。链接:字典序最小做法:从前往后遍历,如果栈空,将a[i]入栈,如果栈顶大于a[i],且栈顶在a[i]之后还出现过,那么栈顶就可以删除。原本我也想到个差不多的做法,可惜方向错了,当时想的是,如果a[i]在后面还出现过,而且不是当前所缺的最小的数,那a[i]就不放入栈中。。这样是会漏解的,如果此时a[i]不放,后面可能出现更大的数字必须要放,字典序就变大了。#include <bits/stdc++.h>// #d

2022-03-22 19:23:07 355

原创 B. Box Fitting (倍增贪心)

B. Box Fitting给定一些高度为1,长度为2的幂次的砖块,要将所有砖块堆叠在长为W的容器里,使得堆起来的高度最小,求最小高度。做法:对于当前层的铺砖块,从最高位往最低位遍历,如果这一位有砖块,且这一层还铺的下这块砖,那就铺上这块砖。就像倍增求LCA一样,从logn往0遍历,能跳就跳。#include<bits/stdc++.h>using namespace std;#define int long longconst int N = 1e6 + 5, mod = 10

2022-03-19 00:01:35 290

原创 2021昆明区域赛

Simone and graph coloring题意:给定一个排列,要求给逆序对连边,形成一张图,图的相邻顶点之间颜色不能相同,问最少的颜色种类以及每个点的颜色。做法:对于每一个数,他要连接上在他前面出现过的比他大的数。如果他前面出现过1 2 3 4 这种颜色,那他的颜色必定是5。可以递归的想,他前面出现过的最大颜色是4,那么对于涂了颜色4的,肯定是出现过1 2 3 的颜色的…,所以线段树查询区间最大值,从而确定当前的颜色。因为多测数据有1e6组,用endl会狂TLE,所以以后再也不要用endl了。

2022-03-17 16:27:15 519

原创 哦~唔西迪西小姐~

哦 ~ 唔西迪西小姐~题意:不好说。。还是老老实实读题吧。做法:冰火都求一下最大值,ans取max即可。都一样求,这里说下火的做法,如果当前火的a[i] >0,那ans += a[i]。再遍历一遍数组,如果此时是火,b[i] = -p[i] - a[i],意思是加上修改的贡献,取消原来的贡献;如果此时是冰,b[i] = -p[i] + max(0, a[i]) ,意思是加上修改的贡献和如果改完能走的贡献。对于b排个序取前m大就好了。还有个优先队列的做法,思路就是不断地push进一些值,维持队列

2022-03-16 11:53:40 283

原创 三角果计数

给一个n个节点的树, 三角果定义为一个包含3个节点的集合, 且他们两两之间的最短路长度a, b, c能够构成一个三角形。做法:和边权没什么关系,画画图发现一条链上所有点都不符合条件,得从这条链上有一个分支,才可以构成合法的。枚举每个点作为下面这样子的中心节点:这里2是中心节点。 1 | 2 / \ 3 4接下来是计数,假设先选上中心的上面的某个点,还有两个点在下面选;然后是三个点都在下面选。#include<bits/stdc++.h>

2022-03-14 22:23:25 964

原创 2021江苏省赛

C. Magical Rearrangement题意:给定10个数字,分别代表0~9有多少。求这些数字组成的最小的数,满足:1.任意相邻的数不相等2.没有前导0(单个的0可以)做法:先不考虑最小,如果最后构造出来了这个串,那么这个串的子串也一定是合法的。即:当前已经构造好了这个串的前一部分,准备要将数字i添加到后面,如果添加之后,剩余的数字能合法的构造,那么才可以添加这个数字。至于能不能合法的构造,考虑最坏的情况,即某一数字出现次数最多,为sum1,其他数字出现次数的和加起来,为sum2,如果

2022-03-10 11:53:02 1056 2

原创 XOR Inverse

给定数组a,求一个x,使得数组每个数异或x得到新数组b,b的逆序对数量最少。如果有多个x符合条件,求最小的x。思路:从二进制角度来看,从最高位开始,如果两个数数位相同,则继续往下看,当数位不同时,两个数就分出了大小,0小1大,那么就会产生顺序对或者是逆序对。当前位如果异或了1之后,顺序对就变成了逆序对,逆序对就变成了顺序对。所以30 * n logn的做法是:从二进制最高位开始枚举,判断此时x这一位填1,是否会得到逆序数更小的数组,不断贪心。注意不要用树状数组求逆序对,要用归并排序。树状数组要离散化

2022-03-08 20:05:12 328

原创 #468. 函数求和

链接:函数求和思路:硬求复杂度不行,这种题一般考虑某某数对答案的贡献,这题考虑 i 对答案的贡献。一个数二进制位最多是k位,先考虑a [1],想让 a[1] & x != a[1],那么 a[1]的二进制位上如果是1,那么对应的x那一位上可以是0,a[1]共有cnt1个位是1,那就有 qpow(2, cnt1) - 1种填法,对于a[1]为0的位,x随便填什么都行。该开始考虑a[2]了,想要在这一位产生贡献,那么首先一定有x & a[1] == a[1],所以上一次搞完之后要有 x .

2022-03-07 11:30:42 199

原创 棋盘从左上角走到右下角方案数

如果无障碍,直接组合数:C(n + m - 2,n - 1)。有障碍,f[i]为不经过前i-1个障碍到达第i个障碍的方案数,把右下角也看成障碍,就能得到答案了。如果第i个障碍左上角有障碍,那么f[i]-=sum[j] * C(x的差,y的差 )。#include<bits/stdc++.h>using namespace std;#define int long longconst int N = 1e6 + 5, mod = 1e9 + 7;int f[N], inv[N];i

2022-03-06 11:37:25 574

原创 摘桃子(推式子+优化)

题目链接:摘桃子题意:有n个数,选连续x个数,如果这些数的和对k取模后的结果也是x,那么算是一种方案。求总方案数是多少。没啥思路,由于以前这种题大多数是推推式子,对着式子展开思路,我也就推了推式子。条件是这样的,对于(L,R)有:R - (L - 1) >= k - 1(sum(R)- sum(L - 1))% k = R - (L - 1)那么就有 sum(R)- R = sum(L - 1) - (L - 1)+ k的倍数。即对于每个sum ( i ),找有多少 sum ( j )

2022-03-05 10:51:21 448

原创 求按位或的最小生成树

Minimum Or Spanning Tree一棵生成树的代价为他所有边的边权按位或得到的值。思路:二进制的题就是要按位考虑。考虑当前这一位是否可以填0,排除掉这一位为0或者是与已经填好的位冲突的边,如果不可以得到一颗生成树,那么这一位只好填1了,否则这一位可以填0。毕竟是cf的题,有思路之后,代码是没有什么难度的。#include<bits/stdc++.h>using namespace std;// #define int long longconst int N = 1e

2022-03-04 23:39:29 314

原创 求区间(L, R)小于k的数有多少个

二位数点典中点。题目链接:数数以前写的博客链接:小沙的remake 那题刚好询问的是小于等于a[i]的数有多少个,所以方法二也很好做,但是这题询问的是其他的数 H[i],所以如果用方法二的话,还得离散化,十分麻烦。用方法一就简单多了,将数组a中小于H[i]的数的下标pos都插入树状数组中,直接查询que® - que(l - 1)就是答案。#include<bits/stdc++.h>using namespace std;#define int long longconst

2022-03-04 18:21:32 470 1

原创 求所有子串的最大值之和

给定数组a,求数组a的所有子串的最大值,对这些最大值求和。链接:子串的最大差思路:直接枚举左端点不会做。考虑一个数对答案的贡献,如果当前的数是a[i],寻找左边第一个大于他的数的pos1,右边第一个大于等于(后面解释为什么是大于等于)他的数pos2,那么在区间[pos1 + 1, pos2 - 1]中,包含 i 的区间最大值就都是a[i]。nlogn做法:从大到小向set中加入 >= a[i] 的数的下标,然后在set中二分找离i最近的数。o(n)做法:单调栈寻找左边第一个大于a[i]的数。

2022-02-28 17:43:36 332

原创 2021 icpc 上海 H. Life is a Game

常规做法是kruscal重构树。但是并查集+启发式合并也能很快的AC这题。给定n个点的点权,m条边的边权,q个询问,每个询问是一开始在点x上,初始能量为k。如果能走到一个点,则k += 点权;如果此时的能量 >= 边权,则能经过这条边。对于每个询问,输出最大能获取的能量。考虑每加一条边,如果连接了两个连通块 fx 与 fy,则 fx 中某一些能量就能更新,剩下的由于能量不够大所以不能更新。如果对边权从下到大排序的话,那么此时不能更新ans的点,以后肯定再也不能更新了。那么如何得知一个点的ans不能

2022-02-26 15:17:59 448

原创 树上启发式合并

先上板子题:cf 600 E给定一棵树,每个节点都有一个颜色;如果颜色c在以x为根的子树中出现次数最多,那么颜色c就是子树x的主要颜色;一棵树可能会有多个主要颜色。求每颗子树的主要颜色的编号之和。考虑暴力dfs:先递归访问x的儿子们,统计好孩子们的答案,怎么统计呢?以y为根的子树为例,访问y这颗树所有节点,用桶统计一下颜色出现的次数,及时更新答案就好了。统计好y的答案后,应该要再访问一遍y这颗树所有节点,因为要删除桶里面的数。所以暴力的复杂度是n2的。暴力大概这样写:int sum, ma;i

2022-02-26 00:27:01 200

原创 bitset和bool哪个更快

前言:牛客2021多校Alice and Bob ,在这题中500050005000的复杂度,用bitset 140ms,bool 493ms。bitset快到起飞。AcWing348–最优比率生成树,这题用bitset会TLE,用bool反而AC。讨论:如果一直连续访问数组中的元素,bool明显快于bitset。bool : 26msbitset : 108ms#include<bits/stdc++.h>using namespace std;#define int lon

2022-02-24 15:42:02 892 1

原创 小G砍树 (换根dp)

小G砍树给你一棵n个节点的带标号无根树。每次,你可以选择一个度数为1的节点并将它从树上移除。问总共有多少种不同的方式能将这棵树删到只剩 1 个点。两种方式不同当且仅当至少有一步被删除的节点不同。思路:先考虑以当前根节点的方案数。设d[x]为x这个节点最后被删除有多少种方案数,那么树形dp一次就可以求出。答案是所有的根节点的方案数之和,所以还需要换根dp。一步一步的来,先考虑怎么进行第一次树形dp,已知子节点y的方案数,怎么求节点x的方案数呢?可以这样想象,y1这颗子树共sum[y1]个节点,把y1这

2022-02-20 17:10:39 737

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除