
算法
记录日常算法训练的一些解题思路。
Mr.琛
钻石要琢磨
展开
专栏收录文章
- 默认排序
- 最新发布
- 最早发布
- 最多阅读
- 最少阅读
-
2020蓝桥杯省赛第一场A组(C/C++)个人题解
文章目录结果填空A. 跑步训练B. 合并检测C. 分配口罩D. 矩阵E. 完美平方数程序题F. 解码G. 走方格H. 整数小拼接I. 超级胶水J. 网络分析结果填空A. 跑步训练【问题】小明要做一个跑步训练。 初始时,小明充满体力,体力值计为 10000。如果小明跑步,每分钟损耗600的体力。如果小明休息,每分钟增加 300 的体力。体力的损耗和增加都是均匀变化的。小明打算跑一分钟、休息一分钟、再跑一分钟、再休息一分钟……如此循 环。如果某个时刻小明的体力到达0,他就停止锻炼。 请问小明在多久后停原创 2020-10-01 10:04:41 · 19318 阅读 · 38 评论 -
洛谷P5019 铺设道路(贪心/分治)
这道题一看到的思路是分治:每次找到最低点,每个坑相应地填最低点的高度,然后divide为最低点左右两部分按此思路继续divide,直到 l>r 时结束。分治的做法按提供的样例可以过,但是分治的时间复杂度在[nlogn, n^2]之间,n最大为1e5规模,如果卡了 n2 的样例会TLE。分治代码:#include<cstdio>#include<cstring>#include<algorithm>using namespace std;const .原创 2020-09-03 15:05:15 · 475 阅读 · 0 评论 -
UVA11624--Fire!(BFS)
题意: 一个人被困在迷宫里,迷宫有若干着火点(注意是若干,有可能不只一个着火点),人每分钟可以跑上下左右一个方向的一个单位距离,火每次会往上下左右四个方向全部烧一个单位距离,求人逃出迷宫的最小时间(出迷宫矩阵外就算逃出),要是不行就输出"IMPOSSIBLE".思路: 很明显是BFS,要是没有火就是一个经典的bfs迷宫问题了。加上着火点的存在后,BFS的方式就变了一下。刚开始还是想一次BFS,...原创 2020-02-10 16:06:00 · 357 阅读 · 0 评论 -
牛客寒假算法集训营3--F【牛牛的Link Power I】(前缀和变式)
题意:思路: 一开始就在想应该跟前缀和或者后缀和有关,因为这道题很直接能想到的就是O(n^2)的遍历每个link点,但是1e5的数据量是会TLE的,但是在前缀和联系怎么两个邻接点的距离卡了一下。其实知道第i-1个link点到其前面的所有link点的能量之和w(i-1),第i个link点到其前面所有link的能量之和则为w(i)=w(i-1)+num(前面的link点数)*(dis(i-1,i)...原创 2020-02-09 12:31:00 · 346 阅读 · 0 评论 -
牛客寒假算法集训营2--C[算概率](概率,递推)
题意:思路:1.当时首先在分数取模那里卡了一下,以为要求逆元,但是其实给的概率就是在取模意义下,要的结果也是在取模意义下的概率,所以其实直接用取模意义下的概率进行概率的求解即可。2.这道题在不考虑时间复杂度的情况下要求出x道题正确的概率很简单,普通的概率乘法公式即可。但是每次都去枚举哪些题正确哪些题错误的话时间复杂度达到了O(n^3)。故要考虑怎么“记忆”当前状态前面已经枚举过的状态,故采用...原创 2020-02-07 12:26:04 · 218 阅读 · 0 评论 -
HDU1024--Max Sum Plus Plus(DP+滚动数组优化)
题意: 给一个序列,把其分成不重复(合法的任意长度)的m段子序列,求最大的m段子段和。思路: DP,由于序列长度达到了1e6,故还需优化空间。dp[i][j]表示以j处元素结尾的i段子段和的最大值;则状态转移方程:(1)dp[i][j]=dp(i,j-1)+a(i) (即a[i]接到元素a[j-1]后面)(2)dp[i][j]=dp(i-1,k)+a(i) (即a[i]自成一段,前面找一...原创 2020-01-30 15:17:33 · 161 阅读 · 0 评论 -
HDU 2126--Buy the souvenirs(01背包+方案数计数)
题意: 有n种纪念品,每种纪念品x元,你有m元,求最多能买多少纪念品及对应方案数。思路: 若不求方案数则为一个普通的01背包问题,每个纪念品的重量为其价格,价值为1;加上求方案数则要在原来的基础上加多一维记录对应的方案数。采用二维的滚动数组求解( dp(2, maxn) ):第一维:dp(0,j)即为01背包最大纪念品数求解,表示容量为j的背包最多能买多少件纪念品。第二维:dp(1,j)为...原创 2020-01-26 11:44:52 · 269 阅读 · 0 评论 -
HDU3348--coins(贪心+思维)
题意: 你有面值为1,5,10,50,100的钱币分别若干张;求购买某一价值的物品所花的最少和最多钱币数。思路:(1)最少的钱币数: 由于面值分别为1,5,10,50,100;大面值都可以由小面值凑数转化而来,故贪心策略适用,从大面值开始枚举,每次取当前能取的最大面值。(2)最多的钱币数: 此时采用贪心策略不再成立了,因为若从小面值开始枚举,当前的最优解并不一定是全局的最优解了。(i.e. ...原创 2020-01-24 17:02:35 · 548 阅读 · 0 评论 -
poj 2676--Sudoku(DFS+回溯)
题意:有t的样例,每个样例会给一个未完成的数独棋盘(数独原理就不解释了吧…每行每列每个小九宫格不能出现重复的数字),编程完成该数独。思路:这道题比较明显的是一道搜索题,故考虑采用DFS,设置布尔数组来标记每行,每列,每个小九宫格已出现的数字,回溯法来试错(有达到终点的解后则停止回溯)。这里二维数组不要开9*9(不够大)!!!(调试了我一个晚上啊啊啊!!!改成10 *10就过了!)#incl...原创 2020-01-20 00:06:28 · 303 阅读 · 0 评论 -
poj 1077--Eight(八数码问题,BFS+康托展开+路径打印)
题意:经典的八数码问题,题目已确定好目标状态,若从起始状态到目标状态有解,输出最短的到达路径的每一步操作;否则输出unsolvable。思路:这是一道经典的八数码问题,采用BFS+康托展开判重,主要多了一步打印路径,把可变化位置x看成数字0放置位置,共有9个数字,即9!种状态,在数组可开的范围内,用pre结构体记录当前状态的前驱状态即转化过来的方式,再用栈倒过来打印答案即可。(BFS时用STL中...原创 2020-01-15 16:41:24 · 595 阅读 · 0 评论 -
POJ 3414 --Pots (BFS+路径输出)
题意: 你有两个罐子,容量分别为a,b;开始时都没水,要通过给定的三种操作,使得其中一个罐子的水量恰好为c,若存在操作使之成立,输出最少操作数及对应的每步操作;否则输出impossible。思路: 由于a,b,c的范围很小为1到100且要求最小操作数,故考虑采用bfs,即搜索可能的情况若有到达其中一个罐子里的水为c的情况则搜索结束并输出路径,否则直到队列为空后输出impossible。对于路径...原创 2020-01-14 20:09:13 · 433 阅读 · 0 评论 -
POJ 3278--Catch That Cow(BFS)
题意:农夫和牛都在一个一维坐标上(0<=x<=100000,这个范围可以用来搜索时剪枝),设农夫坐标为x,每单位时间农夫可以选择到x-1,x+1或者2*x处,而牛不动,求最小时间。由于是求最短时间,故考虑使用bfs,问题可抽象为起始点s到目标点e按上述步骤的最短时间。剪枝:(1)出了范围的坐标就不要再进队了(因为即使还可能回来,对于那三种操作,也不如在范围内的距离较小的点时间优)...原创 2020-01-13 17:32:54 · 185 阅读 · 0 评论 -
poj2431--Expedition (优先队列+思维)
题目如下:题意:牛坐在漏油的卡车上,要到最近的小镇修车,汽车每走一单位距离就要漏一单位油,路途中有n个加油站,给出n个加油站距小镇的距离和能加油量,给出卡车原有的油和出发点到小镇的总距离,求到小镇最少的加油次数(不能到则输出 -1)思路:若牛到达每个加油站都考虑加或不加,就变成有点像复杂动态规划了,这里换一种想法,牛经过加油站假设先把油拿走,但是不一定要加,等到走不动了在取当前走过的里面最大的...原创 2019-11-16 21:00:27 · 160 阅读 · 0 评论 -
HDU1269(有向图强连通分量Tarjan算法)
今天学习有向图的强连通分量,学习了Tarjan算法(其实还有Gabow和Kosaraju算法…),同时,Tarjan对缩点是很有用的。Tarjan算法是基于dfs的,由于任何一个强连通分量,必定是对原图的深度优先搜索树的子树。那么其实只要确定每个强连通分量的子树的根,然后根据这些根从树的最低层开始,一个一个的拿出强连通分量即可。两个贯穿算法的数组:(1)dfn[i]:i结点被首次深度优先搜索...原创 2019-10-27 17:38:25 · 246 阅读 · 0 评论 -
拓扑排序算法总结
拓扑排序算法复习总结:拓扑排序是图论中较为简单的一个算法,思路较为直接。简单而言,由某个集合上的一个偏序得到该集合上的一个全序,这个操作称之为拓扑排序。(贴自百度百科)拓扑排序思路:(1)找入度为0的结点存入答案序列;(2)将与该结点相关的出边删除(相应的结点入度减1);重复上述过程至不存在入度为0的结点。拓扑排序一般用法:(1)拓扑排序通常涉及图中结点的优先级关系,要由一系列结点...原创 2019-10-26 15:43:46 · 1628 阅读 · 0 评论 -
HDU1875(畅通工程再续),并查集+最小生成树
代码如下,含注解:#include<cstdio>#include<cstring>#include<algorithm>#include<math.h>using namespace std;int f[150],sum[150];//f[i]为i的父节点,sum[i]为以i为根节点时其子节点数量; double ans;str...原创 2019-06-11 19:31:12 · 232 阅读 · 0 评论 -
poj1456--Supermarket(贪心+并查集优化时间复杂度)
题意:每天可以买一件东西,每件东西有价值和最后购买的期限,问能获得的最大价值。思路:贪心,肯定先选价值大的,同时最好是在最后期限的时候买,为其他物品留选择空间。第一个是用了并查集优化的,第二个是纯贪心,可以看出时间快了不只1倍。法一:纯贪心,复杂度n*n,数据大一点时可能过不了,按价值排序,直接开一个时间标记数组看是否该天还可以用,这样从价值大到小枚举保证每天买的都是最大价值。#incl...原创 2019-08-21 13:35:03 · 286 阅读 · 0 评论 -
p1031--均分纸牌(思维)
思路:由于第一堆和最后一堆是比其他中间的堆特殊的(因为其只能单方向),考虑从第一堆开始,第一堆只有三种情况,要么拿2的,要么给2,要么什么也不干(废话…),但是这波操作之后第一堆就可以无视了(再重复拿排好的只是在浪费次数),这样第二堆就可以看成是新的第一堆,然后又可以递推下去。在拿下一堆的时候可能出现使下一堆为负数的情况,但也是一样的,相当于提前从后面的堆拿了多的牌。每次拿或给计数加1即可。#...原创 2019-08-21 14:31:15 · 172 阅读 · 0 评论 -
HDU 2141--Can you find it?(二分查找基础好题)
题意:能不能从给定的三个序列中找出满足ai+bj+ck==给定的x值,能则输出YES,否则输出NO。思路:暴搜绝对会超时,由于区间长度为静态,考虑排序后二分(二分的前提一定是有序)。二分有两种选择,其中一种会超时:1.在c中二分查找 x-a[i]-b[j] 是否存在,那么时间复杂度为n * m * log( p )(设a,b,c数组的长度为n,m,p),会超时;2.还有一种更好的方法,先预处理...原创 2019-08-16 19:02:26 · 377 阅读 · 0 评论 -
2019牛客暑期多校(D--Knapsack Cryptosystem)(折半查找)
题意:从n个数中选出若干个数使得和为给定值m,题目保证有解。由于n最大为36,直接搜索2^36次方肯定TLE,但对于区间的一半即18,2 ^18则可以,故应该得想到把区间折半,先计算出前半区间各种组合情况的和,在枚举后半区间各种情况的和sum在前半区间中找m-sum是否存在。法一:set+map#include<cstdio>#include<cstring>#i...原创 2019-08-16 19:54:56 · 156 阅读 · 0 评论 -
牛客--西南民族大学第十届校赛G题 (不想再WA了)(递推)
思路:开始时马上就想组合数学,其实这个题是一个递推的思路,对于每一个A:它只能由前面一个是A或C的字符串转移过来,则其字符串的个数为前面为A的和前面为C的字符串个数总和。而对于C和W,前面每一种情况转移过来都是可以的,故为三种情况字符串的总和。用dp [ i ,0],dp[i,1],dp[i,2] 分别表示长度为i,以A,C,W结尾的字符串的个数。先预处理出dp[1,0],dp[1,1],dp...原创 2019-08-22 19:05:12 · 135 阅读 · 0 评论 -
HDU1512--Monkey King(并查集+左偏树)
题意:一堆猴子刚开始都不认识彼此,要打完架才认识…每次他们会找自己认识的最厉害的猴子打架,打完这个猴子的厉害值减半(向下取整),询问打完后认识的猴子中的最厉害的值(若已经认识输出-1)。思路:用并查集判断是否认识,用左偏树去维护大根堆,实现快速合并。注意:每次删完根节点要把它子节点和距离置空,不时合并时会MLE…#include<cstdio>#include<cstri...原创 2019-08-26 11:04:19 · 170 阅读 · 0 评论 -
HDU--6514(Monitor)(二维差分,前缀和)
题意:每个监控都监控到一个矩形区域,问给定的矩形区域能不能完全被监控覆盖。思路:如果对每个监控内的范围每次都去逐个改变的话会TLE…这时候类似一维前缀和差分的思想,采用二维差分,思想和一维类似,只是把图拓展到二维,由于监控重不重复覆盖都是覆盖的情况,所以差分处理后要把非0数(即监控次数)全部置为1,然后再去求所求矩形面积是否等于该范围内监控覆盖的面积即可。代码如下:(由于n*m=10^7的数据...原创 2019-08-28 13:35:36 · 510 阅读 · 0 评论 -
HDU2454--Degree Sequence of Graph G(Harvel定理判断是否可简单图化)
题意:问以该序列为节点度数是否可简单图化;思路:采用度序列将序列值从大到小排序,每次贪心取出最大度的点(如果该度数已经大于剩下的节点数-1了直接return false,因为这种情况不可图),将其度置为0,将其与剩下的节点逐一连上一条边(连上边的节点的degree–),若出现负边则说明存在环或者平行边,return false,若循环出现度数为0的个数==节点数,return true。(可简单...原创 2019-08-28 21:54:12 · 1520 阅读 · 1 评论 -
洛谷P1080--国王游戏(数学+贪心+大数: python / java)
题意:思路:任取队列中的两个相邻位置来推,假设位置为 i 和 i+1,设位置前面已经积累的左手金币数量为X,对于位置i,ans1=max(X/bi, Xai/ b(i+1))(设max内为y1,y2),交换两位置:ans2=max(X / b(i+1),Xa(i+1)/bi)(设max内为y3,y4),显然,y3<=y2,y1<=y4; 要使ans1<ans2(即前面一种排法...原创 2019-09-09 21:44:41 · 580 阅读 · 0 评论 -
牛客--最优屏障(栈+前缀后缀模拟)
思路:由于屏障作用后使得隔离两侧的哨兵彼此不能看到另一侧,即只能在同一侧内观察,故要试图找出出每个隔离位置前面及后面的防御力,由于屏障的隔离性,选择用一个类似前缀数组,一个类似后缀数组来分别存从1-i每个位置往前看和往后看的防御力值,由于上述式子的限定,其实对于每一个位置,在看的一座较高山后面的较矮山都看不到了,由于从头到目标的前一个位置都要求一个高度递减的单调性,故采用栈结构来存每座山,遍历时...原创 2019-09-17 20:31:46 · 453 阅读 · 0 评论 -
牛客--Forever97与寄信(数论,哥德巴赫猜想)
思路:由于收费是按最大因子收费,故拆成素数用的钱比较少(除自身外只有1),若本身是素数就不拆了,收费1元;若不是素数由于n是在10 ^8以内,故可根据哥德巴赫猜想:对于大于2的偶数可以拆成两个素数,对于大于7的奇数可以拆成3个素数;故先判断是否为偶数,若是偶数,拆成两个素数,收费两元;若不是偶数,分两种情况:1. n-2是素数,这样的话就可以拆成2和n-2(2比较特殊,一个是素数的偶数),花费两...原创 2019-09-21 15:36:33 · 218 阅读 · 0 评论 -
poj1733--Parity game(带权并查集解决区间问题+离散化)
题意:有一个长度为n的01串,每次给出m个范围,判断第一次出现矛盾的位置。思路:由于01串长度为1e9远大于数组所能容纳的范围,而m只有5000组,故离散化预处理一下,由于区间权值非奇即偶,又是一个循环圈的问题,且只有两个元素,故模2,取1为奇,0为偶(因为奇+奇==偶((1+1)%2=0),偶+偶= =偶((0+0)%2=0)),权值动态转移时用向量加减法即可。注意点:由于所给的是闭区间,故...原创 2019-08-21 10:57:58 · 232 阅读 · 0 评论 -
洛谷P3377--(数据结构--左偏树)
题意:合并堆及删除堆中最小元素。思路:采用一般的二叉堆可以实现删除操作,但是要合并的话就会爆,因此引进了左偏树这个数据结构,可在logn时间内实现合并操作。左偏树的性质:1.堆的性质2.左子节点的距离大于右子节点的距离正是利用这些性质实现堆的快速合并。代码如下:(其中并查集的路径压缩会破坏掉树的结构,因此在路径压缩后要将所有相邻节点的父节点都置为当前的根节点)#include<...原创 2019-08-25 16:15:14 · 177 阅读 · 0 评论 -
POJ3614 Sunscreen (贪心+优先队列)
POJ 3614,求最多满足情况的牛的数量。贪心:将牛的最小值从小到大排,防晒值也从小到大排,在最小值小于防晒值的牛中,优先选择最大值小的,因为这样其他最大值大的有更多选择空间,对于最大值的比较用优先队列实现。代码如下:(含注解)#include<cstdio>#include<cstring>#include<algorithm>#include...原创 2019-07-31 19:26:09 · 251 阅读 · 0 评论 -
HDU1176免费馅饼(逆向动态规划)
HDU 1176,每秒都有可能有馅饼落在轴上某点处,每秒只能到所站点,所站点左右去拿馅饼,求能拿到的最多馅饼数。要逆向考虑,类似于数塔问题,从最后时刻一直转移到起始时间。dp[ t,x ]表示t时刻在x处能拿到的最多馅饼数,dp[0,5]为最终状态。状态转移方程:1.左端点:dp[i,0]=dp[i,0]+max(dp[i+1, j],dp[i+1, j+1])2.右端点:dp[i,10...原创 2019-08-04 16:37:45 · 342 阅读 · 0 评论 -
HDU 1114(完全背包变式)
HDU 1114,问装满存钱罐的最小价值是多少。完全背包的变式,限制条件为装满。#include<cstdio>#include<cstring>#include<algorithm>using namespace std;const int INF=0x3f3f3f3f;int main(){ //背包问题变式:要求背包恰好装满,只要在初始化...原创 2019-08-04 15:40:56 · 417 阅读 · 0 评论 -
POJ 3255(迪杰斯特拉算法求次短路)
POJ3255,问题是求节点1到n的次短路。在dijkstra求最短路算法的基础上进行变形,用两个数组分别记录源点到各节点最短路径和次短路径;每次更新时,都将最短路的节点及可能成为次短路的节点push入队;#include<cstdio>#include<cstring>#include<algorithm>#include<queue>...原创 2019-08-04 12:04:25 · 612 阅读 · 0 评论 -
Ants(POJ 1852)/Piotr's Ants(UVa 10881)思维题
对于POJ这道,题目并没有问区别ants的问题,故直接利用不同蚂蚁相撞视作穿过对方即可。对于UVa这道,不同蚂蚁的输出顺序不同,思路:1. 先按照不同蚂蚁能够穿过对方,求出该蚂蚁能到达的地方,在该处一定有一只蚂蚁能够到达; 2. 不同蚂蚁在t秒前后相对位置不变的,因为蚂蚁实际上并没有穿过对方,故按距离左端点排序t秒后仍是该顺序。POJ1852:#include<cstdio>#...原创 2019-07-30 14:56:29 · 208 阅读 · 0 评论 -
POJ 3984 迷宫问题(bfs + 最短路径打印)
题目:POJ3984,从左上方起点到右下方终点寻找最短路径并打印#include<cstdio>#include<cstring>#include<algorithm>#include<queue>using namespace std;//含有路径记录,vis在路径记录中存在作用,故不能简单的设为0,1; int mp[10][10];...原创 2019-07-30 10:45:21 · 412 阅读 · 0 评论 -
POJ1321(棋盘问题)dfs深搜回溯入门
类似N皇后问题,但是它不一定放满,所以要加上回溯环节;代码(含注解)如下:#include<cstdio>#include<cstring>#include<algorithm>#include<iostream>#include<math.h>using namespace std;bool vis[15];char...原创 2019-06-07 12:58:30 · 181 阅读 · 0 评论 -
杭电1010(Tempter of the Bone),dfs深搜入门好题
正在入门搜索,从dfs开始,听说这道题很好,做了(WA了好多次)之后感觉的确很好。这道题包含多种剪枝及回溯。思路:对于每个可行点,从上下左右四个方向去dfs,同时剪去不必要的答案;剪枝:奇偶剪枝,时间剪枝;代码含详细注解;代码如下:#include<cstdio>#include<cstring>#include<algorithm>#incl...原创 2019-06-07 11:13:17 · 177 阅读 · 0 评论 -
线段树区间合并:杭电3308,杭电1540(C/C++)
线段树的点更新和区间查询是入门操作,但是加了一个区间合并就难了些,刚入门线段树第一次做区间更新的题(无从下手啊…),区间合并要考虑的东西很多,因此要维护的东西也就多了,这题有三个变量要维护:含左(右)端点的最长上升长度(用于区间的合并),及整个区间的最长上升长度(真正要的东西)。细节定成败。题目如下:AC代码(含详细注释!!!debug好久才AC的…)主要是query函数的操作要考虑到...原创 2019-04-08 23:09:12 · 215 阅读 · 0 评论 -
线段树基础入门题(点更新,区间查询)杭电1754(C/C++)
线段树是一种非常有效降低时间复杂度的数据结构,利用二分原理将区间不断在树结构中放小直至变为点。基础题(我开始学线段树,这是AC的第一道线段树题…)题目如下:AC代码:(含详细注解,这个真的很详细呀!!!)#include<cstdio>#include<cstring>#include<algorithm>using namespace std...原创 2019-04-04 19:19:12 · 814 阅读 · 0 评论 -
多维费用的01背包,杭电4501(C/C++)
hdu.4501题目链接题目如下:这种背包问题是第一次见到,它又不同于二维费用背包(二维费用背包两维费用同时消费),这个可以选择消费钱,积分或者使用免费兑换的机会,因此需要比较每种情况下的解,找出最优的那个。由于数据量小,直接四重循环(我也只会四重循环…)AC代码:(含注解)#include<cstdio>#include<cstring>#include&...原创 2019-03-26 21:51:32 · 551 阅读 · 0 评论