ACM算法题目列表中简单题解题报告。
题目列表参考链接:
http://byhh.net/cgi-bin/bbscon?board=Algorithm&file=M.1217986350.A&num=3509&start=3491
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
动态规划部分:(BY LIRUQI)
pku1837
一个平衡木上有若干个钩子。还有一些砝码。钩子的位置相对于悬挂点的坐标在[-15,15],砝码的重量在[1,25]。钩子最多有20个,砝码最多有20个。问有多少总不同的摆放方法,使得平衡木达到平衡
这一题数据有比较强的迷惑性,因为数据规模和范围都很小。动态规划的最优子结构也不好找。开始我想到的是把状态定义为在某种砝码使用状态下,到达某个钩子位置的时候,可形成的力矩的集合。但是这样的动态规划复杂度太高了。在设计状态的时候,我们需要保证状态的总数量最少。实际上,这个问题应该这样定义状态:扫描砝码,使用前n个砝码,到达每一个力矩不同方法的个数。状态定义好了以后,动态规划就不难了。
pku1276
需要纪录使用个数的01背包。
pku3267
动态规划。最优子结构为:前若干个字符串形成一个正确的msg至少需要删除多少字符。
uav3752 / World Finals - Tokyo - 2006/2007
http://acmicpc-live-archive.uva.es/nuevoportal/data/problem.php?p=3752
问一个序列最少能够分成多少个不递增的子序列
pku1836
给一个序列,问至少要删除多少点,才能够保证序列中任何一个点左边或者右边所有的数字都小于自身。
动态规划。先从前往后找每个位置的最长递增子序列的长度,从后往前找每个位置的最长递增子序列的长度,然后枚举向左看的点、向右看的点,搜索找到最长的满足条件的序列。然后用原序列长度减去满足条件的序列长度。
pku1260
简单dp,看懂题目意思就会做了。
pku2533 [2007-08-10]
最长递增子序列。
pku3176 [2007-04-27]
简单dp
pku1080 [2007-09-17]
两个串,插入一些’-'使得他们长度相同。两个相同字符之间有一个权值,输出两个串可能的最大权
值之和。
pku1159 [2007-05-12]
given a string, determines the minimal number of characters to be inserted into the string in order to obtain a palindrome.
DP,滚动数组优化。
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
数学部分:(BY LIRUQI)
pku3252 [2007-10-23]
A positive integer N is said to be a ”round number” if the binary representation of N has as many or more zeroes than it has ones. You are to count the round numbers in the inclusive range Start..Finish (1 ≤ Start < Finish ≤ 2,000,000,000).
pku1850 [2007-10-23]
a - 1
b - 2
…
z - 26
ab - 27
…
az - 51
bc - 52
…
vwxyz - 83681
…
给一个代码,求它的编号
组合计数问题
pku1019 [2007-08-15]
形如
11212312341234512345612345671234567812345678912345678910123456789101112345678910
的串,问某个位置的数字
pku1845 [2007-09-28]
A^B的所有自然因数之和,数论
pku1942 [2007-06-22]
组合数
pku2635 [2007-09-18]
K为两个质数的乘积。问K的两个因数是不是都小于L(4 <= K <= 10100 and 2 <= L <= 106).
pku3292
H-合数的个数。以前做过,在poj上没有交。筛选法的应用。
pku2115 [2007-11-02]
循环域
pku3273 [2008-01-19]
二分
pku3258
二分
pku3122
二分
pku1905
二分枚举弧度。在[0,90)的范围内。使得sin(x) / x = L / L`. L,L`分别为原来的长度和弧长。当x < 10^(-4)时候,需要计算其极限:sin(x)/2 -> 1-x/2。因为直接调用库函数计算会产生很大的精度误差。
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
图论部分 (by WUSHAOLIANG)
1860:
题意:已知一个人最开始有一些钱,然后一直有一些货币交换的地方,可以把一种货币以一定的汇率兑换成另外一种,但是要缴纳一定量的手续费,问有没有一种兑换方法使这个人最后的钱能比原来的多。
分析:从最开始的某一种钱的总数可以算出由这种钱直接可以交换得到的钱的最大值,由于手续费是一定的,所以把钱分成两部分分别交换是不划算的。这里可以转换成一个最短路的模型,一直了某一个点最开始离原点的路径长度,问最后这个点能不能达到一个比原始长度更短的路径。这就变成了求一个图里面有没有负环的问题了。
3259:
一个明显的负环检测的题目。
1062:一个单原点单终点的最短路问题。
2253:
题意:已知平面上一些点,问要把两个点连通所需要的最长的边的最小值。
分析:一个最小生成树问题的一个小小的变形。直接从一个点开始做prim并且记录到每一个点所要经过的路上的最长的边的最小值,当达到另外一个点的时候就结束。或者是直接先求出最小生成树,然后在最小生成树上面求结果。
1125:
题意:一直了某些人之间可以互相通信,且知道了他们之间通信所需要的时间,问把一条消息告诉那个人可以使所有的人可能早的得到消息。
分析:求出所有点对之间的最短路,枚举把消息给的人,求出这个人到其他的点的距离的最大值,最后取出一个最小值得到结果。
2240:
题意:和1860一样也是一个货币的转换问是否最后可以得到更多的钱。
分析:大体上和1860是一样的,只是在建图的时候稍微有一点变化。
1789:就是题目意思不是很容易看懂,看懂了过后就是一个很容易的题目了。就是一个最小生成树的题目,最后输出最小生成树的权值,边的权就是两个字符串的差别。
2485:
解法:已知有n个点和每两个点之间的路径,求最小生成树,输出最小生成树的最大权值的边的权值。
1258:
和2485题的意思是一样的,只是最后的输出改成了要输出最小生成树的总的权值,做法和2485也是一样的。
3026:
又是一个读懂了题目意思就比较好做的一个题目,一个简单的最小生成树的题目,最后输出生成树的总权值,但是建图要稍微麻烦一点要对每一个点做一次BFS,求出每两个点之间的最短路。
(*)1094:
题意:已知有N(N<27)个字母,每次告诉一个条件(某个字母在某个字母之后),问最早是在那个地方出现了矛盾或者可以确定所有字母之间的先后顺序了。
解法:在每一个条件之后都做一次拓扑排序,看能不能唯一的确定字母的顺序,或者出现了矛盾。拓扑排序就是每一次找一个入度为0的点,去掉这个点,如果某一次找到的入度为0 的点不止一个的话就是还不能确定所有字母的顺序,如果某一次找不到入度为0的点就是出现了冲突,但是有一个要注意的地方就是要先确定是否有冲突,然后检测是否可以确定顺序(因为有可能出现即不能确定顺序也出现冲突的情况,而且首先检测到的是不能确定顺序,这里检测是否冲突我是用的另外一种方法,因为点比较少,所以可以对每一个点做一次DFS如果发现某一个点指向了一个已经访问过了的点的话就说明出现了冲突)。
(*)3041:
题意:已知在平面上有一些点,一次操作可以去掉某一行或者某一列的所有的点,问最少要多少次操作可以去掉所有的点。
解法:把行作为一个集合的元素,列作为另一个集合的元素,如果位置<i,j>有一个点的话就在第i行和第j列之间连一条边,这样就得到了一个二分图,求这个二分图的最大匹配就是所求的结果。
扩展:
如果求出了最后需要多少次操作后还要求最后的那些操作是哪些的话该怎么做(hoj上的一个题目)。
如果每一个点最少要经过一次操作,但是又不能经过多于一次的操作的话又该怎么做。
3020:
题意:已知了平面上的一些点,一条线段可以覆盖相邻(横坐标相同且纵坐标相差1或者纵坐标相同横坐标相差1)的两个点,问最少要多少条线段才能把所有的点全部覆盖。
解法:横坐标和纵坐标的和为奇数的点作为一个集合,其他的点作为另一个集合,求做大匹配,总的点的个数减去最大匹配数就是结果。
拓展:1*2的砖能不能覆盖一个某些点已经覆盖了的平面。
1459:(不记得题目意思了)
输入的处理比较麻烦 ,但是题目不难。
3436:
题意:某一个工厂要造电脑,一直了每一台机床的速度,需要哪些东西,不能要哪些东西,问该工厂造电脑的最快的速度。
分析;每个机床作为一个点,再加一个起点(什么都没有)和一个终点(有所有的东西),就转化成了一个最大流问题,边上的流量没有限制,但是点上有流量限制,然后把每个点转换成两个点,……。
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
数据结构部分 (by WUSHAOLIANG)
1035:
题意:已知了一些正确的单词,然后问一些单词是否在正确的单词中出现过,如果没有出现过的话,输出所有的改变一个字母,插入一个字母以及去掉一个字母可以得到的正确的单词。
解法:直接硬搞就可以过了。对每一个给的单词,先看是否在正确的单词中出现,如果没有出现的话,再与每一个正确的单词的长度进行比较,如果长度相差的绝对值小于2,则进一步检查。
3080:
题意:已知了最多10个长度为60的字符串,问在所有的字符串中都出现的最长的字串,如果有多个的话输出字典序最小的一个。
解法:枚举第一个字符串的所有子串,看在以后的字符串中是否出现过,在最后取一个最优值就是结果。(这个题目直接用string::find函数就可以过,但是如果数据在大一点应该就要用到KMP了)。
1936:
题意:问一个字符串是否是另外一个字符串的字串。
解法:简单的DP
2388:一个简单的排序的题目。
2299:用归并排序(n lg n的时间复杂度)求逆序数的问题。
3349:
题意:告诉一些雪花的形状(六元组)问是否有两个雪花是一样的(雪花可以旋转和翻转)。
解法:hash,每个雪花只需要插入一次,但是需要查找12次。
3274:
题意:已知了一些长度为K的二进制的数,求最长的一段,是这一段中的每一位出现1的个总数都是相等的。
解法:求从最开始到每一位各个位出现1的总数,减去出现1的最少的那一位的1的个数作为这一个数的权值w,然后从前往后处理,每一次看前面有没有出现过和这一个数的权值相同的数,如果有出现的话更新结果,否则插入这个权值。
2151:一个概率题目。
解法:先DP初始化,然后用余集的性质就可以解答了。
1840:
解法:hash,和已知了5个集合,问有多少种组合的结果为0的题目是一样的。
2002:
题意:已知了平面上的一些点,问这些点可以组成多少个正方形。
解法:枚举两个点,看以这两个点作为对角线上的两个点的正方形的其他两个位置上是否有点存在。
2503:
题意:已知一本字典,求某一些单词的解释。
解法:先排序,然后在二分查找就可以了。用map不知道能不能过。
3253:一个很直接的哈夫曼树的问题。
2513:
题意:已知了一些点,问欧拉路是否存在。
解法:首先检查图是否连通,在连通的条件下看度为奇数的点有多少个,如果有0个或者两个就存在欧拉通路,否则没有。
感觉这一题和trie树没有关系啊。
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
搜索 (by XUHAN)
2488:棋盘遍历,dfs,由于要字典序最小,注意搜索顺序。
3083:求迷宫中从起点到终点的三种路径的长度:摸着左墙走,摸着右墙走,最短路。关于前两种,每一步按照一定的顺序寻找能走方向走即可,已经不算是搜索。
3009:滑砖块游戏,求从起点到终点的最少操作数。Dfs,由于限制了步数,可以在搜索时加以剪枝。
1321:带障碍的皇后问题,dfs,一排排地回溯即可。
2251:迷宫求解,bfs
3278:给定几种运算,求从此数到彼数的最小运算次数,bfs
1426:
3126:和3278类似,bfs
3087:洗牌,模拟
3414:两个桶,无限水,求任意桶里的水为指定体积时的最小操作数。Bfs,对两桶中已有的水进行判重。
2531:将一个无向图的节点分为两部分,使得节点分属两部的边的边权之和最大。我的做法是状态DP,算出所有组合的点集的内部边权之和。比较慢,不知正解。
1416:将一个数断成几节,使得这些数之和小于且最接近一个target number。DFS,和POJ1011有些相似。
2676:Dancing links
1129:平面图着色问题。问一个无向平面图最少用几种颜色实现着色,使得相邻点异色。DFS, 对每个点一次枚举涂(<=当前已有最大颜色编号+1 && 和所有相邻节点不同)的颜色。
~~~~~~~~~~~~~~~~~~~%%% This is a gorgeous split %%%~~~~~~~~~~~~~~~~~~~
几何 (by XUHAN)
2031:三维欧几里德最小生成树,名字比较吓人,规模小,硬搞可矣,[i,j]边权=max(0.0, dis(P[i], P[j])-P[i].r-P[j].r)
1039:用叉积判断方向的经典题。枚举两凸点,先计算过这两点能否出左口,若可以再计算最右能到到多远。
1408:每个单位格子都是四边形,故可以用相同的公式拆成三角形求解
1584:先判断一个简单多边形是否为凸(有模板),然后判断其内部能否装下一个给定(大小和位置)的圆。计算圆心到所有边所在直线的最小距离。
2187:计算点击中最远点对的距离。凸包+(枚举 || 旋转卡壳)
1113:凸包(裸)