一些常见错误/技巧/结论总结
会把考试/做题时犯得不太容易发现的错误记录下...
错误
1.在$Trie$图/$trs$图上乱搞时,注意可能需要把$fail$树/$parent$树中节点的贡献传递给子树
2.斜率优化$DP$,尤其注意别把$i,j$打反了!
3.空间不要开小了!线段树4倍,$SAM$2倍,$dfs$序2倍,邻接表2倍
4.某种情况不合法时,可能需要同时去掉原本的贡献和负贡献
5.LCT的rotate函数需要特判y节点是否为根!
6.主席树相加减时,节点权只支持加减运算,不支持max or min
7.异或的值域可能比原来大,例如原值域是1e6,异或后可能变成$2^{20}$
8.区间修改线段树别忘了下推标记!!!并且在区间覆盖修改的线段树中,注意值域范围,有些时候需要开两个数组(一个记录是否被更新过,一个记录更新成了什么)
9.splay某个节点的信息更新后,必须转到根节点以更新整棵树
10.大模数哈希注意元素值域
11.多测时清空邻接表的头 字符串也尽可能清空 注意多测题目的数据范围!!仔细读题并计算数据范围
12.网络流题目的点边数组大小,网络流和SAM都要init处理边的编号
13.造极限数据,特别大和特别小
14.有的题目会卡行末空格,但注意循环里加入行末空格特判时,如果不能进入循环,则回车也不会输出!!
15.线段树区间操作,if(R>mid) 不能直接else
16.double有效精度只有15位,有效位数多于15位时精度会炸,比如取模不能写1e18+7
17.st表预处理内层循环不要越界
18.dp时要注意目标状态是否转移绝对正确。在2021南京g题中,我设计了一个三维dp x y 0/1/2/3,0123是记xy所处的不同状态。然后我为了简化问题强制x<y。转移方程里我是直接转移到dp min(tx,ty) max(tx,ty) 0/1/2/3。但直接这样取min和max,如果让tx和ty产生交换,目标状态的0123也可能会改变
技巧
1.线段树二分找位置时,尽量找前驱后继然后+1/-1
2.在考虑集合计数方面的问题时,如果对单一元素/节点讨论发现很难转移时,考虑从集合的角度思考
3.在讨论联通块类问题时,如果DP方程难以转移,考虑固定一个点再进行讨论
4.正难则反!!!
5.vector的resize功能可以直接拓展容器大小,无需一次次pushback
6.TLE别光顾着检查做法的正确性和代码是否有细节错误,有可能是题目中的细节没有注意到或神奇的性质没有观察到
7.cin可以关掉流同步和绑定:关闭后scanf printf getchar都不能用了 只能全局cin
8.读入和输出也是题面 可能有隐藏的条件 还有一些是在输出之后的explanation或者note里
9.clock 很慢 不要总用
结论
字符串篇
1.一个字符串本质不同的回文串数量是$O(n)$级别