NOIP算法概论-程序员宅基地

技术标签: 算法  基础算法概论  高中竞赛  noip  高中NOIP C++  

之前高一参加比赛前,曾写过总结,主要是提醒自己NOIP所需要的基本算法,以及至少所需要掌握的数据结构。

当然,NOIP,最重要的算法,只有一个,THAT IS “搜索大法”

练好了搜索,今后的所有竞赛,题目哪怕拿不了满分,至少30+,说不定60+。自己脑补一下优化,100分就到手啦。。。

第一篇正儿八经的博客(别管前面那篇):请各位OIER们,一定一定,要练习搜索,必须练习搜索,而且搜索MUST成为你最拿手的算法!!!

今天的主题是算法概论,就是大概提及一下各个算法啦,貌似也有些没提及(那就拜托无所不能的度娘啦,不过有些具体的算法,我会在后面具体提到的)。

AND 这是高一写的稿子,有啥表述不清的,甚至错误的,请各位体谅!

一.基础思想

1.1二分答案

   noip考试中经常会出现二分答案题目,二分答案,其实是一种思想而并非一种准确的算法,多与模拟,贪心,图论算法相结合。比如说noip2015day2第一题跳石头,noip疫情控制,noip借教室等好多题都可以考虑这种思想。尤其是题目中出现了最大值最小或是最小值最大一般都是二分答案。所以,考试时必须时刻提醒自己要注意往二分答案这方面想。那么二分答案为什么难呢,其一是压根就没往这方面想,其二就是很难check()。check()才是二分答案的关键,容易的直接贪心模拟,比如去年的跳石头,但疫情控制则是二分答案+倍增+贪心的组合题。

那么对于如何书写好check,那就只能靠个人能力了。不过,我们思考时一定要抓住当前分出的答案mid,想好如何会使所求解不满足于当前答案,当发现所求解>mid时该怎么办。从这几个方向去思考会比较容易的得出答案。

1.2贪心

   贪心可以是最不靠谱的解法,也可以是最靠谱的解法。一切都要看你如何去贪,再你码完搜索不会写时,贪心可以帮你。不过除非你百分之百确定贪心的正确性,最好不要只交个贪心上去。贪心其实与最难的dp有很多相像之处,但最大的区别就是有无后效性。这类题目在noip中出现也很多,容易题有不少,但是很多难题多多少少有些思想在其中。这一部分只能考试前多刷题,提高思考能力,考试时自己好好想。    

1.3分治

   分治也是思想,有太多的数据结构,算法要用到分治了。二分答案虽然被我拿出去那是因为太重要了,但二分答案说到根本还是分治思想。分治可以对于多个对象分,答案可以分,操作可以分,最常见的还是算法分治。也就是用分治算法解题,比如:解方程,求平面各种点对等等题目。

1.4倍增

   倍增也是几乎年年多考的题目,倍增,就是字面上的意思,成倍的增长,成倍的跳跃。可以在树上倍增比如说求解lca,在图上同样也可以倍增。倍增多适用于询问很多,但很少修改的题目。如果修改多的话,多用线段树,树链剖分维护。倍增需要注意的地方就是先前的预处理上,以lca举例,预处理时我们求解x的祖先时就要注意(1<<i)<dep[x]。求lca时,先求出两者的差,从小到大枚举,保证(1<<i)&t,使得两者处于同一高度,然后从大到小枚举,保证每次两者的祖先不相等的情况下跳跃。考试时打完倍增一定要注意认真检查,倍增中有很多细节,万一你从大到小搞反了,马上就是0分。

1.5动归

   动态规划,一直以来OIER考试中最难的题目类型。动归也是我最差的算法,难就难在难设计状态,难在如何根据状态找出关系,推出方程。当然,对于这类题目也不是全无办法,最好的就是搜索,把搜索的状态设计好后就可以打出记忆化搜索,记忆化虽然逊色于动归,但如果状态设计的好切题也不是问题。动归在考前就一定要从简单模板开始打起,先把各钟模板打好,然后在认真思考想方法将模板复杂度减小(其实很有用,很多考试都会考模板,但关键是你能否看出来,看出来后能否保证不会超时)。动归考的是个人的分析题目能力,这只能靠多写题,多思考,多请教别人来提高。

二.图论

2.1 SPFA

SPFA是Bellman-ford算法的优化,其实就是在此基础上加了个队列优化,使得只有每次被更新的才会进入队列。SPFA算法时间复杂度更Dijkstra+堆差不多,但是相比而言,Dijkstra+堆更加稳定。

2.2 Dijkstra+heap   

    迪杰斯特拉加堆与SPFA一样,都是求单源最短路径,也就是一个起点,一个终点。但要比SPFA稳定的多,并不容易被随意卡掉。NOIP中此算法用的很多。代码详见资料。

2.3树链剖分

    树链剖分针对的是树上的操作,通常题目要么对于树上是有修改操作的,要么则是求树中一条路径上的最大值/最小值/其它与边息息相关的。

2.4 LCA

    树上最近公共祖先,这个考点一直以来考得很多。之前考得货车运输就是一道裸的lca题目,还有好几题都需要运用到lca。求lca大概有三种方法。第一种就是倍增,倍增在求lca中用的极多,也很好写,只要不把for的顺序搞反一般就没事了。树链剖分也可以求解lca,这一般是比较难的题才用的,因为树链剖分支持树上权值修改,虽然不好打,但可以快速修改,快速询问。第三种是树状数组求lca,用的比较少,就不说了。

2.5拓扑排序

    拓扑排序是在有向无环图上进行的操作,作用是求出一个先后顺序。当然,拓扑排序也可以起到判断有无环,若有环,那么一定进行。在noip考试中拓扑排序考得并不多,但是当我们看到要求操作的先后顺序时,拓扑排序就大有作用了。算法很简单,每次选入度为0的点加入拓扑序列,将与此点直接连通的所有点的入度全部减一,由此重复下去直到不满足为止。

2.6生成树

    生成树在noip考试中用的很多,最小生成树,最大生成树更是经常用到。虽然考试不见得会考裸题目,但是很多题目都得先用生成树将图转变为树后,再在树上进行操作。求最小大生成树都是用克鲁斯卡尔,即贪心思想+并查集。这类题目很灵活,但关键是分析具体题目并求解。

2.7 tarjan

    tarjan算法才是图论中的重难点。tarjan算法用处很多,诸如:求强连通分量,强连通图,割点,割边(桥),还可以将求出的强连通分量缩点。

算法主要部分就是dfs,其中起关键作用的就是low[]数组和dfn[]数组。两个数组都是记录dfs访问到的时间的,low数组是指最早访问到的时间,dfn数组则是指最近一次访问到的时间。

求强连通分量,每一次递归时low[u]=dfn[u]=index++;index是访问时间,而在通过u节点扩展时,若发现(u,v)相连,且v节点未被访问过,那么low[u]=min(low[u],low[v]);(意思就是说因为v是u的子节点,若发现之前曾访问过v节点,则此时更新low[u]的值)。若发现v已经访问过了,那么low[u]=min(low[u],dfn[v]),意思就是说让子树根的low编号最小。当发现low[u]==dfn[u]时就可以判定此点为强连通子图的根,那么此时就可以直接让控制stack的sp指针-,将元素出栈输出了。若要求连通图,想必也是这里动手脚

求割点:若low[v]>=dfn[u],则u为割点,节点v的子孙和节点u形成一个块。因为这说明v的子孙不能够通过其他边到达u的祖先,这样去掉u之后,图必然分裂为两个子图。这样我们处理点u时,首先递归u的子节点v,然后从v回溯至u后,如果发现上述不等式成立,则找到了一个割点u,并且u和v的子树构成一个块。

求桥:若low[v]>dfn[u],则(u,v)为割边。但是实际处理时我们并不这样判断,因为有的图上可能有重边,这样不好处理。我们记录每条边的标号(一条无向边拆成的两条有向边标号相同),记录每个点的父亲到它的边的标号,如果边(u,v)是v的父亲边,就不能用dfn[u]更新low[v]。这样如果遍历完v的所有子节点后,发现low[v]=dfn[v],说明u的父亲边(u,v)为割边。

2.8缩点

    缩点在noip考试中经常会用到,缩点一般是用并查集将所有连通块求出。通过fa数组即可知这n个点将会被缩成几个点,可以用于优化。除此,由于tarjan算法可以求出强连通分量,所以tarjan也可以进行缩点。

2.9强连通分量

    前面tarjan算法中曾介绍过此算法,在此不做介绍。

2.10 二分图

    二分图匹配也是图论的重要算法,求最大匹配可以用匈牙利算法,求最大完美匹配则是用KM算法,虽然它们的理论复杂度并不低,但实际上却是跑的很快。二分图与网络流密不可分,由于难度问题,在联赛中考的不多。

2.11 网络流

    网络流分为费用流和最大流。两类题目几乎不考,当然,如果没有其他方法,也可以往网络流这方面想。

2.12 并查集

    最基础的图论算法之一,前面写了蛮多用到并查集的算法(生成树,缩点),有很多题目都可以用并查集来维护。思想很简单,每个点最初都是一个独立的连通块,若有边与之相连,那么就将它们fa值赋为一样,即在同一连通块中。

三.字符串处理

3.1 kmp

    KMP算法是最基础的字符串算法,用于字符串快速匹配。算法很简单,核心思想就是失败数组的运用,但利用kmp算法的过程出一些比较鬼的题目。比如说:codevs上的动物园,

3.2哈希

    哈希算法很好写,hash[i]=hash[i-1]*p+s[i],p一般取31,而mod一般为1e9+7。对于字符串的子串的哈希值等于hash[r]-hash[l-1]*(p^(r-l+1))。

四.搜索

4.1 DFS

    DFS作为最基本的暴力算法,每一场考试都会考。要注意设计DFS的状态,还要注意不会走回头路。但是,在迷宫等求解方案的时候还是多用BFS。

4.2 BFS

   BFS一般相对DFS用的少一些,多用于迷宫路径求解。

4.3 记忆化搜索

     记忆化搜索并不是每道题都可以的,有些题可以,也有些题不行。一般如果满足无论何时到达此点,此点和到达此点之后的状态都不变的情况下就可以用记忆化搜索。如果重复到达此点后状态发生了改变那么记忆化搜索就不适用了。记忆化搜索是解决可以dp的问题的好方法之一。当然,设计的状态也一定要设计好。

 

 

五.其它

5.1 快速幂

快速幂就不多说了吧,算法的核心是将x^y用二进制来乘,与矩阵快速幂一样。

Res=x;while(y>0) if(y&1) res=res*x%mod;x=(x*x)%mod,y>>=1;这样就可以使速度达到log级别。

5.2 高精度

    高精度是个很麻烦的东西呀,现打很容易出现错误。但是,有些题目,满分only高精度。这一方面,自己一定要多练习,搞清原理后,有事没事打一打。嘿嘿?

5.3 逆序对

    求解逆序对有两种方法,要么归并排序,要么用树状数组求解。考试中考的还是挺多的,一般都是序列问题。后面会具体介绍。

5.4 离散化

     是否离散化,跟题目类型,题目数据有很大关系,请各位出门左转,度娘搜一波,满满的方法。

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/LORD_ZEUS/article/details/82955286

智能推荐

Postgresql 数据库时区(timezone)设置,以及TIMESTAMPTZ和TIMESTAMP数据类型的选择-程序员宅基地

文章浏览阅读2.1w次,点赞12次,收藏18次。timestamp和timestamptz都占用8个字节,在存储时间时并没有本质的区别,都不携带时区信息。只是在insert保存数据和select给数据库客户端返回数据时处理方式不同。下边以具体示例解释这两种数据类型的差别,以及他们与数据库链接时区(session对应的时区)和postgresql数据库时区之间的关系。下边例子使用的数据库时区是Etc/UTC (GMT + 0),首先创建表,然后做相应操作:test_db=> CREATE TABLE test_table ( _timestamptz

模拟鼠标点击按钮的简单示例_bat脚本控制鼠标点击-程序员宅基地

文章浏览阅读7.2k次。原理 首先枚举到目标按钮所在程序的窗口,然后在该窗口内枚举控件获取控件的句柄,获取到按钮的句柄后可通过SendMessage或者PostMessage来发送消息模拟鼠标点击按钮等交互方式。但是因为枚举窗口和句柄都是使用WIN32 API,所以只能枚举到WIN32的控件,对于那些不是微软提供的控件则表示无能为力了。本示例简单地模拟一个往打字机里面写入数据,点击确认的方法。_bat脚本控制鼠标点击

筷云解读企业上云:为什么上云?选什么上云?_企业上云和用户上云啥意思-程序员宅基地

文章浏览阅读611次。近段时间,大家都在说企业上云,那么到底什么是企业上云?企业为什么要上云?应该怎么上呢?在新旧动能转换的关键时期,企业上云的确是可以驱动流程创新和业务创新,成为企业新的利润增长点。筷云作为国内知名的互联网生态体系构建者,以云服务为核心,赋能数字经济为使命,在助力企业上云方面有着丰富的经验。企业上云是什么?企业上云是指企业通过网络,将企业的基础设施、管理及业务部署到云端,利用网络便捷..._企业上云和用户上云啥意思

node、 node-sass 和sass-loader的版本对应问题_node-sass 版本-程序员宅基地

文章浏览阅读2.1k次。错误产生原因:node、 node-sass 和sass-loader的版本对应问题。_node-sass 版本

Java中的静态和非静态(有代码实例,超详细!)_java 静态-程序员宅基地

文章浏览阅读1.8k次,点赞10次,收藏39次。静态变量和方法是属于类的,而不属于类的实例或对象。它们可以通过类名直接访问,不需要创建对象。因此,静态成员常常用于描述与类本身有关的信息,比如常量、工具方法等。例如,Math类中的PI常量和abs()方法都是静态的。非静态变量和方法则是属于类的实例或对象的。它们必须依赖于对象的状态,才能进行相应的操作。因此,非静态成员常常用于描述类的实例状态,比如具有不同属性的学生或员工对象。例如,一个Person类中的name和age变量就是非静态的。_java 静态

关于tecplot动画的制作_tecplot动图-程序员宅基地

文章浏览阅读1.2w次。原文地址:关于tecplot动画的制作作者:Cherry参考文献一:http://hi.baidu.com/zhaoyj_111/blog/item/7939c318bb71e37cdab4bdbe.htmltecplot——画等高线和做动画的流程2008-10-10 11:22 Tecplot构筑结构网格有两种方式:point format和blockformat。_tecplot动图

随便推点

kohana 框架简单小结_kohana框架-程序员宅基地

文章浏览阅读1.7k次。kohana 框架是一个相对比较小众的php框架 ,是有一个开源组织开发的mvc框架。(1)Controller 篇1.接受参数$this -> request -> param('key') 返回的是route路由里定义的参数Arr :: get($_GET, 'key') 获取的是GET作用于里key对应的值2. 重定向$this -> requ_kohana框架

智谱AI发布新一代基座大模型GLM-4;机器学习书籍推荐_glm书籍-程序员宅基地

文章浏览阅读1.1k次,点赞23次,收藏17次。智谱AI发布了全新的基座大模型GLM-4,性能可比GPT-4,拥有超强的中文能力和长文本处理能力。GLM-4的全面跃升在综合能力上提升了60%,支持更长的上下文,具备更强的多模态功能,支持更快的推理,更多并发,推理成本大大降低。智谱AI还发布了定制化的个人GLM大模型GLMs和GLM Store,实现了全家桶能力,让模型自主根据用户意图,自动理解、规划复杂指令,自由调用多种能力,从而完成更加复杂的任务。_glm书籍

在preferenceScreen中加入自己设计的layout布局_能否在perferencescreen中加入linearlayout-程序员宅基地

文章浏览阅读4.9k次。本文来自:点击打开链接图1中上面的listtitle是一个listPreference,当你点击后会出现图2的效果,然后在图2中选择ABC其中一个,这个dialog会消失,并将选择的文本显示在图1中而下面的部分是在PreferenceScreen中嵌套一个PreferenceScreen,在内部的PreferenceScreen中使用android:@layout/your_layou_能否在perferencescreen中加入linearlayout

项目研发管理经验交流_研发经验分享-程序员宅基地

文章浏览阅读10w+次,点赞6次,收藏26次。最近,大BOSS要求我给集团内部的各项目研发组长进行一次培训,让我准备下,我当时一听有点懵,为什么是我? 内心挣扎了200ms后,我爽快的答应了! 回来后,我就在想,我要怎么做这个PPT呢?我当时想的不是我能不能完成,而是我要怎么结合自己这近一年的研发管理经验,来把这个PPT完成的很有料! 既然让我做,就有让我做的理由,我很忙,也没时间去想,咱也不敢说,咱也不敢问..._研发经验分享

spring-security入门4---自定义登录成功和登录失败的行为_spring sso 自定义登录错误-程序员宅基地

文章浏览阅读1.6k次。项目源码地址https://github.com/nieandsun/security_spring sso 自定义登录错误

TypeError: an integer is required (got type is tuple)-程序员宅基地

文章浏览阅读7.6k次。TypeError: an integer is required (got type is tuple ),这个错误。从字面意思理解,需要获取一个整型数据,而原代码是元组。需要做的就是,定位到错误的具体那行,将元组改为整型就行。我这边的是img_tr = [transforms.RandomResizedCrop((int(args.image_size), int(args.image_size)), (args.min_scale, args.max_scale))]将 (int(args.i_an integer is required

推荐文章

热门文章

相关标签