自定义博客皮肤VIP专享

*博客头图:

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

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

博客底图:

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

栏目图:

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

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

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

原创 Docker入门

Docker

2022-10-20 17:06:41 406 1

原创 Thrift客户端服务器示例

Thrift

2022-10-15 18:11:52 670

原创 git 常用命令以及细节

Linux

2022-10-06 16:25:41 278

原创 PAT 1066 AVL树模板

AVL模板

2022-09-17 22:46:22 259

原创 tmux & vim常用命令

111

2022-07-28 23:38:54 160

原创 Linux常用文件命令

111

2022-07-26 23:01:17 116

原创 整数划分(完全背包变形&背包问题求方案)

传送门题面思路Code二维版本#include <bits/stdc++.h>using namespace std;typedef long long ll;const int N = 1e3 + 10;const int MOD = 1e9 + 7;ll f[N][N],n;void solve(){ int n; cin >> n; for(int i=1;i<=n;++i) f[i][0]

2022-05-01 12:06:54 250

原创 E. Preorder(树哈希)

传送门题意思路所以问题主要在于如何确定两颗树是否本质不同;这里使用树哈希,哈希函数如下;当前节点的值为A,那么就取P0P_0P0​;为B,则取P1P_1P1​其中P0,P1P_0,P_1P0​,P1​为两个大的素数,depth为深度;Code#include <bits/stdc++.h>using namespace std;typedef long long ll;const int N = (1<<19) + 10;const int MO

2022-04-30 15:30:11 669

原创 P2343 宝石管理系统

宝石管理系统(Splay维护重复元素)这题的Splay维护关键字是元素的值,而不是序列下标;传送门题面Code#include <iostream>#include <cstring>#include <cstdio>#include <algorithm>using namespace std;typedef long long ll;const int N = 200000 + 10;struct Tree{ int

2022-04-16 14:40:57 293

原创 P4197 Peaks(主席树+Kruskal重构树+倍增)

传送门前缀知识Kruskal重构树题面思路看到困难值小于等于x就应该想到用Kruskal重构树了;首先我们构建一颗Kruskal重构树,然后询问是问我们从某个点uuu出发,不超过困难值hhh,那么这个过程我们可以用倍增来解决;接着看到第kkk大,那么维护第kkk大可以用很多数据结构;假设当前不超过困难值hhh这个点为rtrtrt,因为每个rtrtrt都不同,维护的区间也不同,因此是一个动态区间第k大,因此我们考虑主席树来解决;我们用一个数组range(i)(2)range(i)(2)r

2022-04-15 20:54:55 488

原创 双指针模板

核心思路首先打一个O(n2)O(n^2)O(n2)的暴力,然后考虑性质;当i,j具有单调性的时候,那么我们才可以用双指针来优化;例题最长连续不重复子序列传送门题面思路我们用rrr表示右指针,lll表示左指针;假设r向右移动的时候,l向左移动才是最优解;我们维护[l,r]表示当前的最长不重复的子段,那么当l向左移动才是最优解,那么就说明我们之前l指针向右移动是非法的;也就是说我们可以用向左移动的l替换掉当前的l,使得答案最优,那么就是不移动的情况;Code#include <i

2022-04-13 21:55:12 379

原创 单调队列优化DP

模型求一段区间(窗口)最值的时候,当然这个窗口不需要固定大小,只要保证首尾是递增的即可;见经典模型滑动窗口;如何使用按照常规DP思路定义好状态,写好转移方程(保证正确性)和其他优化方式一样,对转移方程做等价变换;例题最大子序和题面思路时间复杂度是O(n)O(n)O(n)的;注意一个点,子序列的长度不能为空!!因此我们滑动窗口的右边框是当前点iii往左边移动一个位置;Code#include <iostream>#include <cstring>

2022-04-12 20:54:50 1065 1

原创 第十三届蓝桥杯省赛C++B部分题解

统计子矩阵传送门题面思路直接拿二维前缀和去暴力枚举是O(n4)O(n^4)O(n4)的,500肯定跑不过;假设当前我们已经固定了左右边界,只有上下是变化的情况,如下图;那么此时一个子矩形由于左右是固定的,那么相当于给定我们一个一维数组,求连续一段区间和小于等于k的区间数量;这个问题可以使用双指针O(n)O(n)O(n)来解决;那么枚举左右边界是O(n2)O(n^2)O(n2),双指针是O(n)O(n)O(n),那么时间复杂度就是O(n3)O(n^3)O(n3);Code#incl

2022-04-11 17:54:32 691

原创 阶乘分解(考虑每个数是谁的因子)

传送门题面思路直接暴力的对[1,n][1,n][1,n]每个数去分解的话,时间复杂度是O(nn)O(n\sqrt{n})O(nn​)的,会TLE;这种思路也就是看看每个数有哪些质因数;我们现在反过来思考,每个数能够成为哪些数的质因数;也就是反过来枚举;比如素数ppp,有n/pn/pn/p个倍数,它们包含一个ppp;但是p2p^2p2也是包含ppp的,因此我们还需要加上n/p2n/p^2n/p2;依次类推,p3,p4,...p^3,p^4,...p3,p4,...都是需要计算的;即对

2022-04-08 21:33:59 533

原创 找最大环、最小环、第一次出现的环

Link-Cut Tree传送门本题是找第一次出现的环;题面思路二进制有一个常见的性质21+22+...+2i<2i+12^1+2^2+...+2^i <2^{i+1}21+22+...+2i<2i+1那么本题其实也就是要我们求第一次出现的环;那么考虑用并查集来处理(类似Kruskal),然后dfs一次;Code#include <iostream>#include <cstring>#include <cstdio>#i

2022-04-05 21:37:50 454

原创 Codeforces Round #779 (Div. 2) D(0-1Trie)

这里放的是Hard的题面,思路Easy和Hard都有前缀知识戳这D2. 388535 (Hard Version)题面Easy版本的不同在于L=0L=0L=0;思路首先考虑Easy版本的情况,那么原序列中必然存在一个000,那么操作以后这个数就是xxx;题目的数据肯定是有解的(因为没有让我们判断无解的情况),那么也就是说我们求出xxx以后,异或每个数得到的必然是序列[L,...,R][L,...,R][L,...,R]的某种排序;那么实际上我们只需要假设当前的数就是xxx,然后去找和它异

2022-04-02 20:04:47 230

原创 二分图判定&二分图最大匹配模板

二分图定义可以把所有的点划分成两个集合,集合内部不存在边,集合之间存在边;01染色判定二分图性质一个图是二分图等价于不存在奇数环奇数环是指点的个数是奇数的环,如下图;有一个通俗的解释,奇数个点无法被两种颜色均分;那么我们的做法很简单,如果一个点没有被染色,那么我们将它(记为uuu)染为白色,将与uuu相连的点染成黑色;不断重复这个过程即可,若过程中发现同色相连,那么就产生矛盾了;染色法判二分图题面Code#include <iostream>#include

2022-03-31 21:28:53 654

原创 二分图例题

常见问题最小点覆盖、最大独立集、最小路径点覆盖(最小路径重复点覆盖);注意二分图一般是指无向图,后续例题虽然存在有向图,但是思路还是无向图的;常见性质一个图是二分图等价于图中不存在奇数环等价于染色法不存在矛盾最大匹配数 = 最小点覆盖 = 总点数 - 最大独立集 = 总点数 - 最小路径覆盖例题关押罪犯传送门二分 + 染色法判定二分图题面思路把罪犯看成点,把仇恨关系看成边,仇恨值看成边权;那么问题就转化为将所有点分成两组,使得各组内边的权重的最大值尽可能小;因为这是一

2022-03-31 20:46:52 901

原创 Damaged Bicycle(期望 + 状压DP)

题面思路假设当前单车是now,前一个单车是pre;如果前一辆单车是好的,那么我们直接骑走;如果前一辆单车是坏的,那么我们有两种决策;1.直接摆烂,走路去学校2.寻找当前的单车(当前的单车也有好也有坏的情况,按这个思路循环即可全部求解)f(s,i)f(s,i)f(s,i)表示已经遍历过的自行车集合为sss,最后一次停留在iii点;然后按上述思路进行DP即可;因为我们只涉及3个点,起点、自行车、终点,我们不需要每个点都跑最短路,只需要在每个自行车点跑最短路即可;Code#

2022-03-30 12:30:24 870

原创 状压DP第二部分

题面思路前提知识:位运算枚举子集f(s)f(s)f(s)表示状态sss的人已经过河,所花费的最少时间;转移也很容易想到,枚举状态sss的子集来转移,对于多出来的部分暴力计算即可;代码中f[s] = min(f[t] + time,f[s]);其实换成f[s] = min(f[sub] + time,f[s]);也是对的;但是sub为0的情况也是合法的,因此循环的写法要注意Code#include <iostream>#include <cstring>#incl

2022-03-27 23:16:39 428

原创 位运算枚举子集模板

位运算枚举子集模板给定n个元素,问这n个元素组成的每一个集合的所有子集;for(int s=0;s<(1<<n);++s){ for(int sub=s;sub;sub=(sub-1)&s){ //do something } }原理是这样的;集合S的任何一个子集,在二进制表示下,必然可以通过若干次-1得到;那按照这个思路,我们的算法流程如下;假设S0 = S,S0为要枚举的子集,S为集合;S0 - 1判断S0是否是S的子集

2022-03-27 23:11:39 589

原创 翻转括号序列(线段树 + 二分)

传送门题面思路操作一把括号改变我们令( = 1,) = -1,那不就是变成了区间乘以-1即可;查询最右边的合法’)’首先考虑最暴力的思路,就硬for,暴力查询[L,i][L,i][L,i]的和,看看是否为0,这肯定是TLE的;那么我们考虑优化;我们考虑维护一个前缀最小值lmn;然后用二分找区间[L,n][L,n][L,n]最后一个lmn >= 0的点r1;这样[L,r1][L,r1][L,r1]的lmn≥0,且是r1是最大的,且这里面可能存在解;我们是要找某个最大的点

2022-03-22 19:20:29 589

原创 Splay

定义Splay是一颗平衡二叉树,但是往往没那么平衡,期望高度是log(n)log(n)log(n)应用不仅支持普通平衡树的操作,包括一些区间问题(一般用线段树解决)的也支持;保证高度的思想对某个结点进行操作的时候,将其旋转到树根;这里的操作指的是像插入,查询等等;也就是说,这跟操作系统的局部性原理类似,某个点既然当前用到了,那么后续肯定还会用到;拉到根结点其实就是进行了一个类似缓存的操作;应用这个思想,就能保证平均意义下,一次操作的时间复杂度是O(logn)O(logn)O(logn)级

2022-03-11 20:14:48 718

原创 第45届ICPC昆明刷题

比赛传送门传送门G-Gift题面思路首先有一个坑,2021年的2月是没有29号滴;归纳一下题意,我们对于每个朋友可以有三种选择;不搭理他给他做蛋糕送他礼物不难发现,礼物与做蛋糕是可以独立开来的;我们首先考虑礼物;因为礼物数量很少(至多15),我们可以考虑暴力枚举(选或不选)来完成,花费时间为O(2M)O(2^{M})O(2M),当然也可以用DP来解决;接着假设只有做蛋糕,没有送礼物这一说;f(i,j)表示前i个人,做cake不超过j天得到的最大价值f(i,j)表示

2022-03-05 19:34:41 587

原创 卡特兰数列(Catalan)

简介卡特兰数又称卡塔尔数,是组合数学中一个常出现在各种计数问题中的数列。其前几项为: 1, 2, 5, 14, 42, 132, 429, …朴素递推公式快速计算公式应用栈进出问题二叉树结点问题括号序列问题括号化问题:一个合法的表达式由()()()包围,()()()可以嵌套和连接,如:(())()(())()(())()也是合法表达式,现给出nnn对括号,求可以组成的合法表达式的个数;假设当前要计算的是第kkk个(((;其左边有k−1k-1k−1个(((,右边有n−kn-kn−k

2022-03-04 16:23:59 2358

原创 The 15th Jilin Provincial Collegiate Programming Contest

传送门题面思路首先按照题目意思打了个暴力dfs;typedef long long ll;const int MOD = 998244853;int qpow(int x,int y){ ll base = x,ret = 1; while(y){ if(y&1){ ret *= base; ret %= MOD; } base *= base; base %= MOD; y >>= 1; } return ret;}#def

2022-03-04 13:31:17 507

原创 负环 —— SPFA扩展

负环的定义在有向图或无向图中,存在一个环,权值之和为负数;那么按常规最短路,就会无限在这上面更新了,也就是使得dist(u)=−INFdist(u) = -INFdist(u)=−INF负环的问题最经常结合01分数规划;方法建议使用第二种方法,一般来说,方法二跑的比较快;方法一解释这个方法是由Bellman−FordBellman-FordBellman−Ford扩展过来的;BF算法告诉我们,如果我们迭代了nnn次,还有节点没更新,那么说明存在负环;而我们的SPFA是基于BF算法的,在

2022-02-22 17:43:59 433

原创 最小生成树的扩展应用

引入首先介绍一个定理,以及一个它的推论;定理:任何一颗最小生成树一定包含无向图中权值最小的边推论:给定一张无向图G=(V,E)G=(V,E)G=(V,E),n=∣V∣n=|V|n=∣V∣,m=∣E∣m=|E|m=∣E∣。从EEE中选出k<n−1k<n-1k<n−1条边构成GGG的一个生成森林。若再从剩余的m−km-km−k条边中选n−1−kn-1-kn−1−k条添加到生成森林中,使其成为GGG的生成树,并且选出的边的权值之和最小,则该生成树一定包含这m−km-km−k条边中连接生成森林的两个不连通节

2022-02-16 14:50:25 536

原创 最小生成树的基础应用

Prim&Kruskal的一个核心思想Prim是每次选择距离最近的边,然后加进来;Kruskal是将边权升序排序,每次连接两个不连通的点;那如何证明这样选择边是正确的?这两个算法的证明思路都是一样的;假设不选当前这条边,最终得到了一棵树,我们将当前这条边加上,必然会形成环;在这个环上,一定可以找出一条长度不小于(因为按两个算法,我们这条边都是最小的)当前边的边,我们用当前这条边去替换找到的这条边,结果一定不会变差(最坏不变,可能变小);例题Kruskal适用于稀疏图,Prim适用于稠

2022-02-14 10:57:26 2952

原创 Floyd算法思路以及扩展应用

牛的旅行传送门这题是Floyd的简单扩展;题面思路题目要求我们连一条边以后,使得新牧场的直径最小;假设左边牧场的直径为d1d_1d1​,右边牧场的直径为d2d_2d2​;因为我们要将这两个牧场连起来,那么假设新的直径为d3d_3d3​;必然有d3≥max(d1,d2)d_3 ≥ max(d1,d2)d3​≥max(d1,d2);因为要求最小,我们期望相等;假设连边以后,构成了一条新的直径;那么组成必然是距离左边点的最远距离+这条路径长+距离右边点的最远距离;我们想要相等,要

2022-02-07 17:15:20 1023 3

原创 最短路计数类问题 —— 最短路扩展

最短路计数题面思路和DP中的计数问题类似;首先我们得先求出最小值是多少;再求出当前这个状态能由哪几个状态转移最小值过来;需要注意,DP问题都是满足拓扑序的,但是图论的问题不一定;因此我们要满足更新是符合拓扑序的;最短路计数首先满足条件是不能存在值为0的环,因为存在的话那么被更新的点的条数就为INFINFINF了;接着,我们需要把图抽象成最短路树,或者称为拓扑图;而我们求最短路一般有三种方法;BFS,适用于边权为1的情况;迪杰斯特拉系列(包括0-1BFS),适用于非负权图;

2022-02-05 21:32:55 523

原创 拯救大兵瑞恩 —— 最短路扩展 DP + BFS

拯救大兵瑞恩题面思路假设没有钥匙和门的概念,这题就是最基础的迷宫问题(从左上到右下一个BFS即可);现在引入了钥匙和门的概念;假设我们当前在(x,y)(x,y)(x,y),要前往周围的四个格子,但是我们只用(x,y)(x,y)(x,y)是无法表示我们手上有几把钥匙的;看到钥匙的种类最多为101010,考虑状压来表示;我们用dist(x,y,s)dist(x,y,s)dist(x,y,s)表示从点(1,1)(1,1)(1,1)出发到点(x,y)(x,y)(x,y)且拥有的钥匙集合为sss的

2022-02-05 17:20:56 822

原创 选择最佳线路 ——单源最短路扩展,多个起点

最短路

2022-01-30 14:56:50 992

原创 Codeforces Round #768 (Div. 2) A ~ E

C题及以后有详细的解释,AB略过;A思路不难想到,最大的放一边,最小的放另一边;Code#include <iostream>#include <cstring>#include <cstdio>#include <algorithm>using namespace std;typedef long long ll;const int N = 1e5 + 10;int a[N],b[N];void solve(){ i

2022-01-30 12:02:35 1216

原创 (转载)什么是P问题、NP问题和NPC问题

看到一篇好文章,收藏一下~点这

2022-01-29 20:37:31 399

原创 Codeforces Round #767 (Div. 2) C~F

C题面思路题目要求我们在满足字典序最大的同时有更多的数字;不难想到,mex(1,n)mex(1,n)mex(1,n)肯定能得到最大的mex;现在我们需要找到一个kkk,使得这个kkk尽可能小的同时满足mex(1,k)=mex(1,n)mex(1,k) = mex(1,n)mex(1,k)=mex(1,n);完成了这一步以后,只需要循环的执行[k+1,n][k+1,n][k+1,n]这一部分即可;基于这个思路,我们维护一个前缀、一个后缀;前缀不断增加,后缀不断减少,直到找到这个kkk为止;

2022-01-27 16:41:29 587

原创 插入、支持删除、查询的MEX数据结构

Mex定义mexmexmex为序列中未出现的最小的非负整数如mex(0,2,1,4,3)=5mex({0,2,1,4,3}) = 5mex(0,2,1,4,3)=5性质只有在添加的数等于当前序列的mex时,mex的值才会变化;添加操作只会使得mex变大;模板struct Mex{ int cnt[N];//cnt(i)表示数字i出现的次数 set<int> st;//记录未出现的数字 multiset<int> mulst;//记录出现过的数

2022-01-27 16:25:53 778

原创 Codeforces Round #759 (Div. 2) D、E

D题面思路首先要知道奇排列和偶排列的概念;对一个数列,如果总的逆序数为奇数,则此排列为奇排列,否则为偶排列;对于一次交换swap(i,j)来说,会改变排列的奇偶性,如下图;而题目要我们执行swap(i,j)与swap(j,k);也就是两次交换,因此排列的奇偶性不变;因此,对于排列来说,我们只需要计算逆序对是奇还是偶,偶数则为YES,奇数则是NO;因为这道题可能有重复的数字出现;比如[3,2,3,1][3,2,3,1][3,2,3,1],下面两种换法是等价的;我们可以设第一

2022-01-25 16:31:10 404

原创 Codeforces Round #766 (Div. 2)

A思路不难想到,答案只能为0,1,2…或者直接-1Code#include <iostream>#include <cstdio>#include <algorithm>using namespace std;typedef long long ll;const int N = 1e2 + 10;char G[N][N];void solve(){ int r,c,x,y; cin >> r >>

2022-01-21 17:22:30 395

原创 Kruskal重构树学习

引入简单来讲,就是在Kruskal算法进行的过程中,我们把最小生成树的边权改为点权;可以看成是Kruskal算法的扩展使用;假设原树有nnn个结点,因为最小生成树是n−1n-1n−1条边;那么重构树有2n−12n-12n−1个结点;举个例子,比如xxx到yyy连了一条边;那么重构以后变成这样;性质是一个小/大根堆(由建树时边权的排序方式决定)所有原来的点是叶子节点LCA(u,v)LCA(u,v)LCA(u,v)的点权是 原图uuu到vvv路径上最大边权的最小值或者最小边权的最大

2021-12-02 00:45:52 540 1

空空如也

空空如也

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

TA关注的人

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