《算法竞赛入门经典》第四章总结

来源:互联网 发布:网络电话录音 编辑:程序博客网 时间:2024/05/01 16:37

例题
4-1

两串字符串都只要,统计不同字符的出现次数,然后排个序,如果从小到大都相等则输出YES,否则输出NO

4-2

好坑= =如果单词已经全部猜完直接跳出,我还以为如果此时如果猜的还有= =任要继续呢

4-3

这题很妙的是用-1,1两种步长来表示两种方向,刚开始我还再想如果到了负数%怎么用,白书更妙的是每次从n-1开始这样增张减少都可以都可以

4-4

这题最终要的就是练习了多行输入= =以后这种多行输入就用他这个函数了,int readchar(){for(;;){int ch=getchar();if(ch!='\n'&&ch!='\r')return ch;}}while(readcodes()){}和再readcodes()中通过来if(ch==EOF)return 0;if(ch=='\n'||ch=='\r')return 1;

4-5

两个方法,感觉都挺妙的,第一种是就是整体模拟这个过程。好方法1.通过一个type把操作统一2.删除中 用if(!cols[i])copy(type,++cnt2,i);插入用if(cols[i])copy(type,++cnt2,0);copy(type,++cnt2,i);3.通过BIG来记录自生原来的位置,(刚开始我还再想要不要开个结构体来存储行和列)第二种是记录操作直接输出所求单元在这一系列变化后的位置。

4-6

这题本身不是很难就是比较烦,注意删除和查找可以统一,以及,对求平均数之类要价格EPS来减小误差。

课后练习题
4-1

刚开是直接判断将是否符合题目的要求,但是发现非常难写,因为还要考虑红方子被吃掉的情况,后来改成,将将朝四个方向都移动一下,然后在新的棋盘上再次判断,这样比较好些 = =因为不知道如果上来将和帅就是相对的这种情况该怎么判= =两个ac的程序给的答案不一样,最后花了快30个小时这题也没有ac掉。处理技巧用数组存放位移量,如将的```dx[]={-1,-1,0,0},dy[]={0,0,-1,-1}for(int i=0;i<4;i++){cnt+check{r+dx[i],c+dy[i]);}模拟出位移四个方向后的情况,这种模拟题最好不要用if else这样比较乱。我刚开始的思路是,每个棋子超它可能的位置,前进如果能碰到将就算将军,这样很麻烦,每个旗子都要检查一遍,如果我们反过来想,检查将周围的情况,看看他是否处于被攻击的状态,这样就比较简单了,注意缩写可以统一的情况比如帅和车的列方向,检查时要注意不要超过棋盘,马的情况也可以用数组来```int hx[] = { -2, -1, -2, -1, 1, 2, 1, 2};  //马将军int hy[] = { -1, -2, 1, 2, -2, -1, 2, 1};int tx[] = { -1, -1, -1, -1, 1, 1, 1, 1};  //马蹩脚int ty[] = { -1, -1, 1, 1, -1, -1, 1, 1};for(int k = 0; k < 8; ++k)   //被马将军    {        tr = r + hx[k], tc = c + hy[k];        if(tr < 1 || tr > 10 || tc < 1 || tc > 9) continue;        if(brd[tr][tc] == 'H' && (!brd[r + tx[k]][c + ty[k]]))为复杂的用一个空间未2的cr,和cc分别储存行和列,如果与将在同一行且前面有个棋子则判成功。注意本身位置可不判,因为将必移动。

4-2

= =我感觉我写的比网上的简洁,思路就是用一个无向图存储两个点之间是否有通路然后从左到友从上到下,正方形周长不断扩大,看看走一圈的周长是否等于该边长应有的周长。网上的思路是最外层是长方形的长度,然后分别从每个点出发寻找

4-3

这题我没有写,感觉思路不太好,自己写会很烦,看的大佬的程序思路就是用一个变量currplay来记录是黑白双方谁动,然后根据三个操作,分别对应模拟,主要是list和Move这两个操作,他们都需要用到一个find函数来判断一个位置放上棋子后是否会有其他棋子变化。move函数首相通过if (!find(r, c, false))来判断是否切下棋者,然后题目告诉了不会出现双方操作都不合法的情况因此,之后紧跟着一个 find(r, c, true);对于list则是一样,对每个位置开始判断是否,可以吃到别的子重点就是find函数,对于他也是用两个数组来存放,周围的位置int dx[8] = { -1, -1, 0, 1, 1, 1, 0, -1 };int dy[8] = { 0, 1, 1, 1, 0, -1, -1, -1 };

4-4

对每个方向都通过一个队列去模拟,如果与本位置,的棋子不一样则继续朝那个方向移动,如果一样则该方向停止,把吃掉的棋子变色其他情况直接跳出。路是一个正方形不动,另一个正方形,分别以6个点环绕一圈,这24种状态只要有一种满足即可,刚开始我以为侧面只要各种颜色,顺序一样即可,后来发现上下面也需要一一对应,不然翻转后,侧面位置不对应

4-5

我的方法比较麻烦完全用字符串来处理的,不太好,网上有个大神直接利用整数做的,而且我刚开始对于怎么排除数字之间的点很是头疼,太蠢了没有想到这样就可以了scanf("%d.%d.%d.%d",&ip[0][i], &ip[1][i], &ip[2][i], &ip[3][i]); 然后将每一块的IP地址排序由于子网掩码只有那九种情况可以用一个数组直接预存下。真是妙啊,主要还是我太蠢。

4-6

刚开始我以为是动态规划 ,直接就没做了先用个数组把莫尔斯密码存起来,然后根据每个字母或者数字的表示,把那些单词组合起来,原来是在尾部,那样的话,每次如果公共前缀相同,距离就是他们的距离差。

4-7

看了代码才把程序看懂我了个去,我想复杂了,就是记录每一行对应的10,x,的位置,如果,x大于等于2这时就没办法知道他们具体是1还是0了,其他通过奇偶性,来确定x的值,和判断该列数据是否合法,根据自顶而下的设计方式,这个程序应该有三个函数main,judge,和print。教训:1.认真观察样例:样例给的原始数据为自上而下,而不是自左向右!2.注意好细节:原文最后讲到:Ifnecessary,addextra‘0’bitsattheend of the recovered data so the number of bits is always a multiple of 4.如果整个数据长度不是四的倍数,则需要补额外的0来达到4的倍数!

4-8

这道题我看了很久,实在想不到如何表示,后来发现题目的(A,B,C)就是一个很好的表示方法,时间用一个for循环表示,定的大一点,如果在这个范围内都没有出现那就输出-1了,没个循环怎家c如果到了睡觉的时候判断能不能不能重新从1开始。

4-9

这题我没看懂题意,看解析的这么简单,注意因为可能会爆int所以用long long.直接暴力搜索A,B,居然都不给A,B范围。

4-10

这题真的很好,重点就是如何找到,水的最终位置是在哪个海拔区间之内,思路1,是每次上升一个海拔,然后用已经加进去的总体积,减去该加的V如果小于零则找到,思路2 把所有格子按海拔顺序排序,逐个计算含水海拔,第n个格子的含水海拔等于(总水量+n个格子相对于0海拔的体积)/n个格子的面积和,顺序读入后面格子海拔,如果此格高于已算出的含水海拔则终止。
0 0
原创粉丝点击